通过实验,使学生掌握向量相似度的基本实现方法。
向量空间模型是信息检索中最重要的形式化模型之一,向量相似度是对向量空间模型评分的重要依据。本实验需要编程实现向量相似度的基本算法实现。
用户输入查询(如 “best car insurance”),文档(如“car insurance auto insurance”),文档总数N的值(如1000000),文档中每个词的文档频率df以及权重机制,可以输出向量相似度的值。
分为权重计算模块与结果展示模块两个功能模块。
def tf(D, D1):
l = len(D)
tf = np.zeros(l)
for i in range(l):
tf[i] = D1.count(D[i])
return tf
def wf(tf, flag):
wf = tf.copy()
l = len(tf)
if flag == 'l':
for i in range(l):
wf[i] = 1 + round(log(tf[i], 10), 2) if tf[i] != 0 else 0
elif flag == 'a':
maxt = max(tf)
for i in range(l):
wf[i] = 0.5 + 0.5*tf[i]/maxt
elif flag == 'b':
for i in range(l):
wf[i] = 1 if tf[i] > 0 else 0
return wf
def idf(N, df, flag):
l = len(df)
idf = [1]*l
if flag == 't':
for i in range(l):
idf[i] = round(log(N/df[i], 10), 1)
return idf
def Wtq(wf, idf, flag):
Wtq = np.array(wf)*np.array(idf)
sq = pow(sum(Wtq*Wtq), 0.5)
if flag == 'c':
for i in range(len(Wtq)):
Wtq[i] = round(Wtq[i]/sq, 2)
return Wtq
def rz(ls):
l = len(ls)
ls1 = []
for i in range(l):
a = ls[i]
ls1.append([str(a), int(a)][int(a) == a])
return ls1
import prettytable as pt
import numpy as np
from math import log
import warnings
warnings.filterwarnings("ignore")
I = input('请输入查询(用空格分割):')
D1 = input('请输入文档(用空格分割):')
N = int(input('请输入文档总数:'))
D = list(set((D1 + ' ' + I).split(' ')))
l = len(D)
df = [0]*l
for i in range(l):
df[i] = int(input('请输入' + D[i] + '的文档频率df:'))
flags = input('请输入权重机制:').split('.')
#I = 'best car insurance'
#D1, N = 'car insurance auto insurance, 1000000'.split(',')
#N = int(N)
#df = list(map(int, '1000, 10000, 5000, 50000'.split(',')))
#D = list(set((D1 + ' ' + I).split(' ')))
#flags = 'nnc.ltn'.split('.')
flagd = [i for i in flags[0]]
flagi = [i for i in flags[1]]
tb = pt.PrettyTable()
itf = tf(D, I)
iwf = wf(itf, flagi[0])
iidf = idf(N, df, flagi[1])
iWtq = Wtq(iwf, iidf, flagi[2])
tb.add_column('word', D)
tb.add_column('I tf', rz(itf))
tb.add_column('I wf', rz(iwf))
tb.add_column('I df', rz(df))
tb.add_column('I idf', rz(iidf))
tb.add_column('I Wtq', rz(iWtq))
dtf = tf(D, D1)
dwf = wf(dtf, flagd[0])
didf = idf(N, df, flagd[1])
dWtq = Wtq(dwf, didf, flagd[2])
tb.add_column('D tf', rz(dtf))
tb.add_column('D wf', rz(dwf))
tb.add_column('D Wtq', rz(dWtq))
neiji = np.array(iWtq)*np.array(dWtq)
tb.add_column('IP', rz(neiji))
tb.align = 'l'
print('\n+' + '-'*25 + 'I表示查询, D表示文档, IP为内积' + '-'*25 + '+')
print(tb)
score = sum(neiji)
print('相似度为:' + str(score))
tb = pt.PrettyTable()创建了结果显示的容器,通过tb.add_column 方法添加列,该过程调用了prettytable 库,用于python中的表格化显示。
运行程序,根据提示进行输入,设置权重机制为nnc.ltn,得到结果如下图。
由图可知权重机制为nnc.ltn时相似度为3.28,设置权重机制为lnc.atn,运行程序得到结果如下图。
注释掉内容为调试过程中代码,预设相关参数,设置权重机制为nnc.ltn,得到结果如下: