k近邻算法--改进约会网站配对效果
k近邻算法采用测量数据点之间的距离的方法进行分类。
样本数据集(训练样本集):样本集中每一数据与所属分类存在对应关系。
新数据分类:将新数据与训练样本集中数据进行比较,提取样本集中特征与新数据最相似(数据点之间的距离最小)的k个点,将这k个点的分类标签作为新数据的分类。
下面用该算法来改进约会网站配对效果,代码来源为《机器学习实战》。
训练样本集特征 :
- 每年飞行里程
- 玩游戏所耗时间百分比
- 每周消费冰淇淋量
训练样本集分类 :
- 不喜欢的人
- 魅力一般的人
- 极具魅力的人
训练样本为文本数据集,需要先转化数据格式:
def fileTransfromMatrix(filename): # 该函数输入为文件名字符串 输出为训练样本矩阵和类标签向量
filedata = open(filename) # 打开文件
numberOfLines = len(filedata.readlines()) # 获取文件数据行数
returnMatrxix = np.zeros((numberOfLines,3)) # 创建空的样本矩阵
classLabelVector = [] # 创建空的类标签向量
index = 0
filedata = open(filename)
for line in filedata.readlines():
line = line.strip() # strip()函数 删除开头结尾处的空白符
listFromLine = line.split('\t') # 按照制表符对行文本进行切片 生成数组文件
returnMatrxix[index,:] = listFromLine[0:3] # 给样本矩阵的第index行(所有元素)赋值
classLabelVector.append(int(listFromLine[-1])) # 给类标签向量添加该样本类别值
index += 1
return returnMatrxix,classLabelVector
在处理不同取值范围的特征值时,需要先将数值归一化,将取值范围处理到[0,1]之间:
def dataNormal(dataSet):
minVals = dataSet.min(0) # 参数0使得函数从所有列中选取最小值
maxVals = dataSet.max(0)
ranges = maxVals - minVals
normalDataSet = np.zeros(np.shape(dataSet))
m = dataSet.shape[0]
normalDataSet = dataSet - np.tile(minVals,(m,1))
normalDataSet = normalDataSet / np.tile(ranges,(m,1))
return normalDataSet,ranges,minerals
接下来就是k近邻算法实现的代码了:
def classifyPerson(inX, dataSet, labels, k): # 输入为预测点 训练样本特征数组 训练样本类别数组 K值
dataSetSize = dataSet.shape[0] # 获取行数
diffMatrix = np.tile(inX, (dataSetSize,1)) - dataSet # 计算预测点与所有欧训练点的差值
sqrDiffMat = diffMatrix**2
sqrDistances = sqrDiffMat.sum(axis=1) # 按行求和
distances = sqrDistances**0.5 # 计算距离
sortedDistIndicies = distances.argsort() # 距离值从小到大排列,返回对应的索引
classCount={}
for i in range(k):
voteIlabel = labels[sortedDistIndicies[i]] # 从小到大取距离
classCount[voteIlabel] = classCount.get(voteIlabel,0) + 1 # 将该点的类别添加到字典中
# sorted函数:返回一个经过排序的列表
# key 指定用于排序的列
# reverse 设置为True时为倒序排列
sortedClassCount = sorted(classCount.items(), key=operator.itemgetter(1), reverse=True)
return sortedClassCount[0][0]
输入一个新的数据,机器判断所属类别:
def classifyNewPerson():
classList = ['Not interest', 'small interest', 'large interest']
flyMiles = float(input('每年的飞行公里数')) #输入新数据三个特征值
playGames = float(input('视频游戏所花时间占比'))
iceCream = float(input('消费的雪糕量'))
datingMatrix,classLabels = fileTransfromMatrix('/Users/Desktop/datingTestSet2.txt')
normalDataSet,ranges,minVals = dataNormal(datingMatrix)
inputData = np.array([flyMiles,playGames,iceCream])
classifierResult = classifyPerson((inputData-minVals)/ranges,normalDataSet,classLabels,3)
print('You will probably like this person : ',classList[classifierResult - 1])

浙公网安备 33010602011771号