最近邻居法(KNN算法,又译K-近邻算法)是一种用于分类和回归的非参数统计方法

算法实现

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
import numpy as np
import operator

def createDataSet():
group = np.array([[1.0, 1.1], [1.0, 1.0], [0, 0], [0, 0.1]])
labels = ['A', 'A', 'B', 'B']
return group, labels

def classify0(inX, dataSet, labels, k):
dataSetSize = dataSet.shape[0]
diffMat = np.tile(inX, (dataSetSize, 1))-dataSet
sqDiffMat = diffMat**2
sqDistances = sqDiffMat.sum(axis=1)
distances = sqDistances**0.5
sortedDistIndicies = distances.argsort()
classCount = {}
for i in range(k):
voteIlabel = labels[sortedDistIndicies[i]]
classCount[voteIlabel] = classCount.get(voteIlabel, 0)+1
sortedClassCount = sorted(classCount,
key=lambda x: classCount[x], reverse=True)
return sortedClassCount[0][0]

笔记

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
import numpy as np
# python中自带的sum对一维数组的求和
a = np.array([1, 2, 3])
print(sum(a)) # 6
sum([1, 2, 3])
a = np.array([[1, 2, 3], [4, 5, 5]])
print(sum(a)) # [5,7,8]
# shape[]函数返回数组某个维度的长度
b = a.shape
c = a.shape[0]
e = a.shape[1]
print(b, c, e) # (2,3) 2 3
a = np.sum([[1, 2, 3], [4, 5, 5]]) # 无参
print(a) # 20
a = np.sum([[1, 2, 3], [4, 5, 5]], axis=0)
# axis=0,表示第一个维度,即按列相加
print(a) # [5,7,8]
a = np.sum([[1, 2, 3], [4, 5, 5]], axis=1)
# axis=1,表示第二个维度,即按行相加
print(a) # [6,14]
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
#dict.get(key, default=None)
# 1. 先定义字典
dict = {'A': 1, 'B': 2}
# 2. 当key值存在于dict.keys()中时,调用get()方法,返回的是对应的value值
print(dict.get('A'))
# 返回为:1
# 3. 当key值不存在于dict.keys()中时,调用get()方法,返回的是None
print(dict.get('C'))
# 返回为:None
# 4. 当default = x时,若key值存在于dict.keys()时,返回dict[key];若不存在于dict.keys()中时,返回x
print(dict.get('A', 0)) # 1
print(dict.get('C', 0)) # 0

x = np.array([1, 4, 3, -1, 6, 9])
x.argsort()
# 输出定义为y=array([3,0,2,1,4,5])。
# 我们发现argsort()函数是将x中的元素从小到大排列,提取其对应的index(索引),然后输出到y。
# 例如:x[3] = -1最小,所以y[0] = 3, x[5] = 9最大,所以y[5] = 5。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
#sorted函数:sorted(iterable,key,reverse)
#其中iterable表示可以迭代的对象,
#key是一个函数,用来选取参与比较的元素,
#reverse则是用来指定排序是倒序还是顺序,
#reverse=true则是倒序,reverse=false时则是顺序,默认时reverse=false

d = {'Michael': 95, 'Bob': 75, 'Tracy': 85}
>>>sorted(d.keys())
['Bob', 'Michael', 'Tracy']
>>>sorted(d.values())
[75, 85, 95]
>>>sorted(d)
['Bob', 'Michael', 'Tracy']#默认就是根据key值排序
>>>sorted(d,key=lambda x: d[x])#根据value值的大小对key排序
['Bob', 'Tracy', 'Michael']

#以下返回值是既包含key又包含value的列表,
#与上面的区别就是sorted的第一个参数不是d而是d.items(),d.items会把d变成一个可迭代对象.
d = {'Michael': 95, 'Bob': 75, 'Tracy': 85}
>>>d.items()
dict_items([('Michael', 95), ('Bob', 75), ('Tracy', 85)])
>>>sorted(d.items(),key=lambda x : x[1])
[('Bob', 75), ('Tracy', 85), ('Michael', 95)]
>>>d = {'data1':3,'da':1,'dat':2,'data22':4,'aa':3,'ff':0}
>>>sorted(d.items(),key=lambda x :(x[1],x[0]))#对dict先根据value排序,value相等的根据key排序
[('ff', 0), ('da', 1), ('dat', 2), ('aa', 3), ('data1', 3), ('data22', 4)]
sorted(d.items())#根据key值对整个dict排序
[('aa', 3), ('da', 1), ('dat', 2), ('data1', 3), ('data22', 4), ('ff', 0)]
1
2
3
4
#lambda 表达式,
#通常是在需要一个函数,但是又不想费神去命名一个函数的场合下使用,也就是指匿名函数。
add = lambda x,y : x + y
print(add(1, 2))

遇到的问题

1.from numpy import * 遇到警告

2.算法实现的第69行 sorted()

以下代码报错:

1
sortedClassCount=sorted(classCount,key=operator.itemgetter(1),reverse=True)