在信息检索导论课程中,涉及到了倒排记录表合并算法的实现,因此在这简单分享一下我的实现的算法。
(1)两个倒排记录表的合并算法
伪代码如下:
算法实现:
'''程序说明:
求两个倒排记录表的交集
输入词项的倒排记录表时,当输入-1,停止输入其倒排记录表
'''
#data字典存储所有数据
data = {}
#分别输入两个词项以及其对应的倒排记录表
#输入词项word1以及它的倒排记录表
word1 = str(input("请输入词项word1:"))
id_1 = []
while 1:
a1 = int(input('请输入word1的倒排记录表(输入-1,停止输入倒排记录表):'))
if(a1 != -1):
id_1.append(a1)
else:
break
data[word1] = id_1
#输入词项word2以及它的倒排记录表
word2 = str(input('请输入词项word2:'))
id_2 = []
while 1:
a2 = int(input("请输入word2的倒排记录表(输入-1,停止输入倒排记录表):"))
if(a2 != -1):
id_2.append(a2)
else:
break
data[word2] = id_2
print('词项a1为:',word1)
print('词项a2为:',word2)
print('词项a1的倒排记录表为:',data[word1])
print('词项a2的倒排记录表为:',data[word2])
#求两个词项的并集
same_id = []
for i in data[word1]:
if(i in data[word2]):
same_id.append(i)
else:
continue
print("相同的倒排记录表为:",same_id)
(2)基于跳表指针的倒排记录表的合并算法
伪代码:
算法实现:
'''代码说明:基于跳表指针求两个倒排记录表的交集
输入词项的倒排记录表时,当输入-1时,停止输入其倒排记录表
'''
import math
#存储所有数据的字典
data = {}
#分别输入两个词项以及其对应的倒排记录表
#输入词项word1以及它的倒排记录表
word1 = input("请输入word1:")
id_1 = []
while 1:
a1 = int(input('请输入word1的倒排记录表:'))
if(a1 != -1):
id_1.append(a1)
else:
break
data[word1] = id_1
#输入词项word2以及它的倒排记录表
word2 = input('请输入word2:')
id_2 = []
while 1:
a2 = int(input("请输入word2的倒排记录表:"))
if(a2 != -1):
id_2.append(a2)
else:
break
data[word2] = id_2
#求两个词项的并集
#两个倒排记录表的长度
len1 = len(data[word1])
#词项word1倒排记录表需要设置的跳表指针的步长
n1 = math.ceil((pow(len1,0.5)))
len2 = len(data[word2])
#词项word2倒排记录表需要设置的跳表指针的步长
n2 = math.ceil((pow(len2,0.5)))
i = j = 0
result = []
count = 0
while i < len1 and j < len2:
if data[word1][i] == data[word2][j]:
result.append(data[word1][i])
i = i +1
j = j + 1
count = count + 1
elif data[word1][i] < data[word2][j]:
while (i + n1 < len1) and data[word1][i+n1] <= data[word2][j]:
i = i + n1
count = count + 1
else:
i = i + 1
count = count + 1
else:
while (j + n2 < len2) and data[word2][j+n2] <= data[word1][i]:
j = j + n2
count = count + 1
else:
j = j + 1
count = count + 1
print("倒排记录表的并集为:",result)
#print("跳转次数为:",count)
(3)输入多个词项与查询时倒排记录表的合并算法
查询优化:
考虑n 个词项的 AND ,按照表从小到大(即df文档频率从小到大)的顺序进行处理,每次从长度最小的开始合并。
算法实现:
'''代码说明:
1、合并多个词项的倒排记录表的查询
2、输入多个词项时,输入skip,停止输入词项,即跳出程序
3、输入词项的倒排记录表,当输入-1时,停止输入其倒排记录表
'''
print('在输入每一个词项的倒排记录表时,输入-1停止输入')
print("在输入词项时,输入skip,停止输入词项以及其倒排记录表")
#存储所有数据的字典
data = {}
data_term = {}
data_key = []
#分别输入两个词项以及其对应的倒排记录表
#输入词项word1以及它的倒排记录表
while 1:
word = str(input("请输入word:"))
if word != 'skip':
id_1 = []
while 1:
a1 = int(input('请输入word的倒排记录表:'))
if(a1 != -1):
id_1.append(a1)
else:
break
#以字典的形式保存word1的词项以及倒排记录表
data[word] = id_1
else:
break
#输出总数据库
#print('所有数据为:',data)
#对数据库中的倒排记录表的长度进行从大到小排序
while len(data)>0:
min_num = 1000
for key in data:
if len(data[key])<=min_num:
min_num = len(data[key])
key_term = key
term = data[key]
#将最短的词项以及其倒排记录表存储到data_term中
data_term[key_term]=term
#将最短的倒排记录表的词项按顺序存储到data_key列表中
data_key.append(key_term)
#在原数据库中删除最短词项相关信息
data.pop(key_term)
#按倒排记录表的由小到大的顺序进行合并
id_term = []
for i in range(0,len(data_key)):
if(i==0):
id_term = data_term[data_key[i]]
else:
for j in id_term:
if(j in data_term[data_key[i]]):
continue
else:
id_term.remove(j)
print('合并后的倒排记录表为:',id_term)
(4)邻近搜索中两个倒排记录表的搜索算法
伪代码:
注意事项:
邻近搜索中的搜索策略考虑两个词项的倒排记录表前后位置之间的距离不大于某个值
算法实现 :
'''
程序说明:
1、邻近搜索中两个倒排记录表的搜索算法
2、k为临近的距离
3、输入词项的倒排记录表时,输入-1,停止输入倒排记录表
'''
#存储所有数据的字典
data = {}
#分别输入两个词项以及其对应的倒排记录表
#输入词项word1以及它的倒排记录表
k = int(input("请输入K的值:"))
word1 = str(input(print("请输入word1:")))
id_1 = []
while 1:
a1 = int(input('请输入word1的倒排记录表:'))
if(a1 != -1):
id_1.append(a1)
else:
break
data[word1] = id_1
#输入词项word2以及它的倒排记录表
word2 = str(input('请输入word2:'))
id_2 = []
while 1:
a2 = int(input("请输入word2的倒排记录表:"))
if(a2 != -1):
id_2.append(a2)
else:
break
data[word2] = id_2
print('词项a1为:',word1)
print('词项a2为:',word2)
print('词项a1的倒排记录表为:',data[word1])
print('词项a2的倒排记录表为:',data[word2])
#求两个词项的并集
#存储相同的倒排记录表
same_id = []
for i in data[word1]:
for j in data[word2]:
if(abs(i-j)<=k):
if(i not in same_id):
same_id.append(i)
if(j not in same_id):
same_id.append(j)
else:
continue
print("相同的倒排记录表为:",sorted(same_id))