Машинное обучение от начального до профессионального (3) - KNN

алгоритм

Алгоритмы машинного обучения (3): предварительное исследование K-ближайших соседей

1 Введение и применение KNN

1.1 Введение в КНН

kNN (k-ближайшие соседи), китайский перевод K-ближайшие соседи. Мы часто слышим историю: если вы хотите узнать финансовый уровень человека, вам нужно знать финансовые возможности только его 5 лучших друзей,
Среднее значение экономического уровня его пяти человек является экономическим уровнем этого человека. Это предложение содержит идею алгоритма kNN.

Пример: как показано выше, к какому классу должен быть отнесен зеленый кружок, красный треугольник или синий квадрат? Если K=3, так как пропорция красных треугольников равна 2/3, то зеленым кружкам будет присвоен класс красных треугольников, если K=5, так как пропорция синих четырехугольников равна 3/5, то зеленым кружкам будет присвоен класс класс синих квадов Квадратный класс.

1) Процесс создания KNN

1 给定测试样本,计算它与训练集中的每一个样本的距离。
2 找出距离近期的K个训练样本。作为测试样本的近邻。
3 依据这K个近邻归属的类别来确定样本的类别。

2) Определение категорий

① При голосовании меньшинство подчиняется большинству. Категория с наибольшим количеством категорий является категорией тестового образца.

② Метод взвешенного голосования, согласно рассчитанному расстоянию, взвешиваются голоса соседей, чем ближе расстояние, тем больше вес, и вес устанавливается как величина, обратная квадрату расстояния.

1.2 Применение КНН

Хотя KNN очень прост, часто говорят, что «дорога проста», и предложение «вещи собираются вместе, люди делятся на группы» может приоткрыть его завесу. Казалось бы, простой KNN может делать как классификацию, так и регрессию.
Его также можно использовать для заполнения пропущенных значений для предварительной обработки данных. Поскольку модель KNN имеет хорошую интерпретируемость, в общем случае для простых задач машинного обучения мы можем использовать KNN как
Базовая линия для каждого результата прогнозирования мы можем объяснить это очень хорошо. В системе Рекомендации также есть тень KNN. Например, в системе Рекомендации статьи,
Для пользователя A мы можем передать статьи, просмотренные k пользователями, ближайшими к A, к A.

В сфере машинного обучения часто очень важны данные, есть поговорка: «Данные определяют верхний предел задачи, и цель модели — бесконечно приближаться к этому верхнему пределу».
Видно, что хорошие данные очень важны, но по разным причинам данные, которые мы получаем, отсутствуют, если мы сможем хорошо заполнить эти недостающие значения,
Вы можете получить более качественные данные, чтобы можно было обучить более надежную модель. Далее давайте посмотрим, как KNN выполняет регрессию и как заполнять пустые значения, если он выполняет классификацию.

2 Лабораторное руководство

2.1 Экспериментальная среда

1. python3.7
2. numpy >= '1.16.4'
3. sklearn >= '0.23.1'

2.2 Цели обучения

  1. Узнайте, как KNN решает задачи классификации
  2. Узнайте, как KNN выполняет регрессию
  3. Узнайте, как KNN заполняет нулевые значения, как использовать knn для построения конвейера с нулевыми значениями.

2.3 Поток кода

  1. 2D набор данных – классификация knn

    • Шаг 1: Импорт библиотечной функции
    • Шаг 2: Импорт данных
    • Шаг 3: Обучение модели и визуализация
    • Шаг 4: Принципиальный анализ
  2. Набор данных Orioles - классификация kNN

    • Шаг 1: Импорт библиотечной функции
    • Шаг 2: Импорт и анализ данных
    • Шаг 3: Обучение модели
    • Шаг 4: прогнозирование и визуализация модели
  3. Смоделированный набор данных - регрессия kNN

    • Шаг 1: Импорт библиотечной функции
    • Шаг 2: Импорт и анализ данных
    • Шаг 3: Обучение модели и визуализация
  4. Данные о коликах у лошадей - предварительная обработка данных kNN + конвейер классификации kNN

    • Шаг 1: Импорт библиотечной функции
    • Шаг 2: Импорт и анализ данных
    • Шаг 3: Заполнение нулевого значения KNNImputer — введение в использование и принцип
    • Шаг 4: Заполнение нуля KNNImputer — расчет евклидова расстояния
    • Шаг 5: Прогнозирование и визуализация на основе модели конвейера

2.4 Алгоритм боя

2.4.1 Демонстрационный набор данных – классификация kNN

Шаг 1: Импорт библиотечной функции

import numpy as np
import matplotlib.pyplot as plt
from matplotlib.colors import ListedColormap
from sklearn.neighbors import KNeighborsClassifier
from sklearn import datasets

Шаг 2: Импорт данных

# 使用莺尾花数据集的前两维数据,便于数据可视化
iris = datasets.load_iris()
X = iris.data[:, :2]
y = iris.target

Шаг 3: Обучение модели и визуализация

k_list = [1, 3, 5, 8, 10, 15]
h = .02
# 创建不同颜色的画布
cmap_light = ListedColormap(['orange', 'cyan', 'cornflowerblue'])
cmap_bold = ListedColormap(['darkorange', 'c', 'darkblue'])

plt.figure(figsize=(15,14))
# 根据不同的k值进行可视化
for ind,k in enumerate(k_list):
    clf = KNeighborsClassifier(k)
    clf.fit(X, y)
    # 画出决策边界
    x_min, x_max = X[:, 0].min() - 1, X[:, 0].max() + 1
    y_min, y_max = X[:, 1].min() - 1, X[:, 1].max() + 1
    xx, yy = np.meshgrid(np.arange(x_min, x_max, h),
                         np.arange(y_min, y_max, h))
    Z = clf.predict(np.c_[xx.ravel(), yy.ravel()])
    # 根据边界填充颜色
    Z = Z.reshape(xx.shape)

    plt.subplot(321+ind)  
    plt.pcolormesh(xx, yy, Z, cmap=cmap_light)
    # 数据点可视化到画布
    plt.scatter(X[:, 0], X[:, 1], c=y, cmap=cmap_bold,
                edgecolor='k', s=20)
    plt.xlim(xx.min(), xx.max())
    plt.ylim(yy.min(), yy.max())
    plt.title("3-Class classification (k = %i)"% k)

plt.show()

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-OD8zDhnA-1638089238606)(output_7_0.png)]

Шаг 4: Принципиальный анализ

Если вы выберете меньшее значение K, это эквивалентно использованию обучающих примеров в меньшем поле для прогнозирования. Например, когда k = 1, данные в точке разграничения легко затрагиваются локально, синяя часть на рисунке. также есть несколько зеленых блоков, главным образом потому, что данные слишком чувствительны локально. Когда k = 15, разные данные в основном разделяются по цвету.При прогнозировании в это время они попадут непосредственно в соответствующую область, и модель будет относительно более надежной.

2.4.2 Набор данных Orioles – классификация kNN

Шаг 1: Импорт библиотечной функции

import numpy as np
# 加载莺尾花数据集
from sklearn import datasets
# 导入KNN分类器
from sklearn.neighbors import KNeighborsClassifier
from sklearn.model_selection import train_test_split

Шаг 2: Импорт и анализ данных

# 导入莺尾花数据集
iris = datasets.load_iris()

X = iris.data
y = iris.target
# 得到训练集合和验证集合, 8: 2
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2)

Шаг 3: Обучение модели

Здесь мы устанавливаем параметр k(n_neighbors)=5, используя евклидово расстояние (метрика=Минковского и p=2)

# 训练模型
clf = KNeighborsClassifier(n_neighbors=5, p=2, metric="minkowski")
clf.fit(X_train, y_train)
KNeighborsClassifier()

Шаг 4: Прогнозирование модели и визуализация

# 预测
X_pred = clf.predict(X_test)
acc = sum(X_pred == y_test) / X_pred.shape[0]
print("预测的准确率ACC: %.3f" % acc)
预测的准确率ACC: 0.933

Давайте посмотрим на процесс обучения и прогнозирования KNN с помощью таблицы. Вот таблица для наглядности:

  1. Данные тренировки [таблица соответствует списку]
feat_1 feat_2 feat_3 feat_4 label
5.1 3.5 1.4 0.2 0
4.9 3. 1.4 0.2 0
4.7 3.2 1.3 0.2 0
4.6 3.1 1.5 0.2 0
6.4 3.2 4.5 1.5 1
6.9 3.1 4.9 1.5 1
5.5 2.3 4. 1.3 1
6.5 2.8 4.6 1.5 1
5.8 2.7 5.1 1.9 2
7.1 3. 5.9 2.1 2
6.3 2.9 5.6 1.8 2
6.5 3. 5.8 2.2 2
  1. Процесс knn.fit(X, y) можно просто рассматривать как хранение таблицы
feat_1 feat_2 feat_3 feat_4 label
5.1 3.5 1.4 0.2 0
4.9 3. 1.4 0.2 0
4.7 3.2 1.3 0.2 0
4.6 3.1 1.5 0.2 0
6.4 3.2 4.5 1.5 1
6.9 3.1 4.9 1.5 1
5.5 2.3 4. 1.3 1
6.5 2.8 4.6 1.5 1
5.8 2.7 5.1 1.9 2
7.1 3. 5.9 2.1 2
6.3 2.9 5.6 1.8 2
6.5 3. 5.8 2.2 2
  1. Процесс прогнозирования knn.predict(x) вычисляет расстояние между x и всеми обучающими данными.
    Здесь мы используем евклидово расстояние для расчета, и процесс прогнозирования выглядит следующим образом.

x = [ 5. , 3.6 , 1.4 , 0.2 ] y = 0 x = [5. , 3.6, 1.4, 0.2] \\ y=0 x=[5.,3.6,1.4,0.2]y=0

Шаг 1: Рассчитайте расстояние между x и всеми данными обучения.

feat_1 feat_2 feat_3 feat_4 расстояние label
5.1 3.5 1.4 0.2 0.14142136 0
4.9 3. 1.4 0.2 0.60827625 0
4.7 3.2 1.3 0.2 0.50990195 0
4.6 3.1 1.5 0.2 0.64807407 0
6.4 3.2 4.5 1.5 3.66333182 1
6.9 3.1 4.9 1.5 4.21900462 1
5.5 2.3 4. 1.3 3.14801525 1
6.5 2.8 4.6 1.5 3.84967531 1
5.8 2.7 5.1 1.9 4.24617475 2
7.1 3. 5.9 2.1 5.35070089 2
6.3 2.9 5.6 1.8 4.73075047 2
6.5 3. 5.8 2.2 5.09607692 2

Шаг 2: Сортировка по номеру в зависимости от расстояния

расстояние в порядке возрастания feat_1 feat_2 feat_3 feat_4 расстояние label
1 5.1 3.5 1.4 0.2 0.14142136 0
3 4.9 3. 1.4 0.2 0.60827625 0
2 4.7 3.2 1.3 0.2 0.50990195 0
4 4.6 3.1 1.5 0.2 0.64807407 0
6 6.4 3.2 4.5 1.5 3.66333182 1
8 6.9 3.1 4.9 1.5 4.21900462 1
5 5.5 2.3 4. 1.3 3.14801525 1
7 6.5 2.8 4.6 1.5 3.84967531 1
9 5.8 2.7 5.1 1.9 4.24617475 2
12 7.1 3. 5.9 2.1 5.35070089 2
10 6.3 2.9 5.6 1.8 4.73075047 2
11 6.5 3. 5.8 2.2 5.09607692 2

Шаг 3: Мы устанавливаем k = 5 и выбираем k ближайших образцов для голосования.

расстояние в порядке возрастания feat_1 feat_2 feat_3 feat_4 расстояние label
1 5.1 3.5 1.4 0.2 0.14142136 0
3 4.9 3. 1.4 0.2 0.60827625 0
2 4.7 3.2 1.3 0.2 0.50990195 0
4 4.6 3.1 1.5 0.2 0.64807407 0
6 6.4 3.2 4.5 1.5 3.66333182 1
8 6.9 3.1 4.9 1.5 4.21900462 1
5 5.5 2.3 4. 1.3 3.14801525 1
7 6.5 2.8 4.6 1.5 3.84967531 1
9 5.8 2.7 5.1 1.9 4.24617475 2
12 7.1 3. 5.9 2.1 5.35070089 2
10 6.3 2.9 5.6 1.8 4.73075047 2
11 6.5 3. 5.8 2.2 5.09607692 2

Step4: k Соседи этикетки голосовать

nn_labels = [0, 0, 0, 0, 1] -> 0 для получения окончательного результата.

2.4.3 Набор данных моделирования – регрессия kNN

Шаг 1: Импорт библиотечной функции

#Demo来自sklearn官网
import numpy as np
import matplotlib.pyplot as plt
from sklearn.neighbors import KNeighborsRegressor

Шаг 2: Импорт и анализ данных

np.random.seed(0)
# 随机生成40个(0, 1)之前的数,乘以5,再进行升序
X = np.sort(5 * np.random.rand(40, 1), axis=0)
# 创建[0, 5]之间的500个数的等差数列, 作为测试数据
T = np.linspace(0, 5, 500)[:, np.newaxis]
# 使用sin函数得到y值,并拉伸到一维
y = np.sin(X).ravel()
# Add noise to targets[y值增加噪声]
y[::5] += 1 * (0.5 - np.random.rand(8))

Шаг 3: Обучение модели и визуализация прогнозов

# #############################################################################
# Fit regression model
# 设置多个k近邻进行比较
n_neighbors = [1, 3, 5, 8, 10, 40]
# 设置图片大小
plt.figure(figsize=(10,20))
for i, k in enumerate(n_neighbors):
    # 默认使用加权平均进行计算predictor
    clf = KNeighborsRegressor(n_neighbors=k, p=2, metric="minkowski")
    # 训练
    clf.fit(X, y)
    # 预测
    y_ = clf.predict(T)
    plt.subplot(6, 1, i + 1)
    plt.scatter(X, y, color='red', label='data')
    plt.plot(T, y_, color='navy', label='prediction')
    plt.axis('tight')
    plt.legend()
    plt.title("KNeighborsRegressor (k = %i)" % (k))

plt.tight_layout()
plt.show()

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ie01EAHk-1638089238610)(output_25_0.png)]

Шаг 4: Анализ модели

Когда k = 1, прогнозируемый результат связан только с самой последней обучающей выборкой.Из кривой прогноза видно, что переобучение легко происходит, когда k мало.

Когда k=40, предсказанные результаты относятся к последним 40 выборкам, потому что у нас есть только 40 выборок, что является средним значением всех выборок в это время, и все предсказанные значения являются средними в это время, что склонно к недооснащению.

В общем, при использовании knn мы попробуем из [3, 20] в соответствии с размером данных и выберем лучшее k, Например, [3, 10] на приведенном выше рисунке относительно хорошо по сравнению с 1 и 40 выбирают .

2.4.4 Данные о коликах у лошадей — предварительная обработка данных kNN + конвейер классификации kNN

# 下载需要用到的数据集
!wget https://tianchi-media.oss-cn-beijing.aliyuncs.com/DSW/3K/horse-colic.csv
# 下载数据集介绍
!wget https://tianchi-media.oss-cn-beijing.aliyuncs.com/DSW/3K/horse-colic.names
/bin/sh: wget: command not found

Шаг 1: Импорт библиотечной функции

import numpy as np
import pandas as pd
# kNN分类器
from sklearn.neighbors import KNeighborsClassifier
# kNN数据空值填充
from sklearn.impute import KNNImputer
# 计算带有空值的欧式距离
from sklearn.metrics.pairwise import nan_euclidean_distances
# 交叉验证
from sklearn.model_selection import cross_val_score
# KFlod的函数
from sklearn.model_selection import RepeatedStratifiedKFold
from sklearn.pipeline import Pipeline
import matplotlib.pyplot as plt
from sklearn.model_selection import train_test_split

Шаг 2: Импорт и анализ данных

2,1,530101,38.50,66,28,3,3,?,2,5,4,4,?,?,?,3,5,45.00,8.40,?,?,2,2,11300,00000,00000,2
1,1,534817,39.2,88,20,?,?,4,1,3,4,2,?,?,?,4,2,50,85,2,2,3,2,02208,00000,00000,2
2,1,530334,38.30,40,24,1,1,3,1,3,3,1,?,?,?,1,1,33.00,6.70,?,?,1,2,00000,00000,00000,1
1,9,5290409,39.10,164,84,4,1,6,2,2,4,4,1,2,5.00,3,?,48.00,7.20,3,5.30,2,1,02208,00000,00000,1
2,1,530255,37.30,104,35,?,?,6,2,?,?,?,?,?,?,?,?,74.00,7.40,?,?,2,2,04300,00000,00000,2
......

Введение набора данных:horse-colic.names

«?» в данных представляет собой нулевое значение.Если мы используем классификатор KNN, «?» не может быть числовым и не может быть рассчитан, поэтому нам необходимо выполнить предварительную обработку данных, чтобы заполнить нулевые значения.

Здесь мы используем KNNImputer для заполнения нулями.Исходное заполнение KNNImputer очень просто.Вычислите ближайшие k выборок каждой выборки и выполните заполнение нулями.

Давайте сначала посмотрим на принцип работы KNNImputer:

Шаг 3: Заполнение нулевого значения KNNImputer — введение в использование и принцип

X = [[1, 2, np.nan], [3, 4, 3], [np.nan, 6, 5], [8, 8, 7]]
imputer = KNNImputer(n_neighbors=2, metric='nan_euclidean')
imputer.fit_transform(X)
array([[1. , 2. , 4. ],
       [3. , 4. , 3. ],
       [5.5, 6. , 5. ],
       [8. , 8. , 7. ]])

Формула расчета евклидова расстояния с нулевым значением

nan_euclidean_distances([[np.nan, 6, 5], [3, 4, 3]], [[3, 4, 3], [1, 2, np.nan], [8, 8, 7]])
array([[3.46410162, 6.92820323, 3.46410162],
       [0.        , 3.46410162, 7.54983444]])

Шаг 4: Заполнение нуля KNNImputer — расчет евклидова расстояния

Выборка [1, 2, np.nan] Ближайшие 2 выборки: [3, 4, 3] [np.nan, 6, 5], при вычислении расстояния используется евклидово расстояние, и речь идет только о непустых выборках.
[1, 2, np.nan] заполняется [1, 2, (3 + 5)/2] = [1, 2, 4]

нормальное евклидово расстояние
Икс знак равно [ 3 , 4 , 3 ] , у знак равно [ 8 , 8 , 7 ] ( 3 - 8 ) 2 + ( 4 - 8 ) 2 + ( 3 - 7 ) 2 знак равно 33 = 7,55 х знак равно [3, 4, 3], y = [8, 8, 7] \\ \sqrt{(3-8)^2 + (4-8)^2 + (3-7)^2} = \sqrt{33} = 7,55 x =[3,4,3],y=[8,8,7](3−8)2+(4−8)2+(3−7)2​=33​=7,55

Евклидова кластеризация с нулями
x = [1, 2, np.nan], y = [np.nan, 6, 5] 3 1 (2 − 6) 2 = 48 = 6,928 x = [1, 2, np.nan], y = [ np.nan, 6, 5] \\ \ sqrt {\ frac {3} {1} (2-6) ^ 2} = \ sqrt {48} = 6,928 x = [1,2, np.nan], y =[np.nan,6,5]13​(2−6)2 ​=48 ​=6,928
Вычислите только все ненулевые значения и взвесьте все нули для расчета ненулевых значений.В приведенном выше примере мы видим, что у одного есть 3 измерения, и только второе измерение не равно нулю.
Добавьте расчеты для первого и третьего измерений ко второму измерению, все умноженные на 3.

Метрика расстояния в таблице использует евклидово расстояние с нулевым значением для расчета сходства и использует простое средневзвешенное значение для заполнения.

Образец с нулевыми значениями ближайший образец 1 ближайший образец 2 значение после заполнения
[1, 2, np.nan] [3, 4, 3]; 3.46 [np.nan, 6, 5]; 6.93 [1, 2, 4]
[np.nan, 6, 5] [3, 4, 3]; 3.46 [8, 8, 7]; 3.46 [5.5, 6, 5]
# load dataset, 将?变成空值
input_file = './horse-colic.csv'
df_data = pd.read_csv(input_file, header=None, na_values='?')

# 得到训练数据和label, 第23列表示是否发生病变, 1: 表示Yes; 2: 表示No. 
data = df_data.values
ix = [i for i in range(data.shape[1]) if i != 23]
X, y = data[:, ix], data[:, 23]

# 查看所有特征的缺失值个数和缺失率
for i in range(df_data.shape[1]):
    n_miss = df_data[[i]].isnull().sum()
    perc = n_miss / df_data.shape[0] * 100
    if n_miss.values[0] > 0:
        print('>Feat: %d, Missing: %d, Missing ratio: (%.2f%%)' % (i, n_miss, perc))

# 查看总的空值个数
print('KNNImputer before Missing: %d' % sum(np.isnan(X).flatten()))
# 定义 knnimputer
imputer = KNNImputer()
# 填充数据集中的空值
imputer.fit(X)
# 转换数据集
Xtrans = imputer.transform(X)
# 打印转化后的数据集的空值
print('KNNImputer after Missing: %d' % sum(np.isnan(Xtrans).flatten()))
>Feat: 0, Missing: 1, Missing ratio: (0.33%)
>Feat: 3, Missing: 60, Missing ratio: (20.00%)
>Feat: 4, Missing: 24, Missing ratio: (8.00%)
>Feat: 5, Missing: 58, Missing ratio: (19.33%)
>Feat: 6, Missing: 56, Missing ratio: (18.67%)
>Feat: 7, Missing: 69, Missing ratio: (23.00%)
>Feat: 8, Missing: 47, Missing ratio: (15.67%)
>Feat: 9, Missing: 32, Missing ratio: (10.67%)
>Feat: 10, Missing: 55, Missing ratio: (18.33%)
>Feat: 11, Missing: 44, Missing ratio: (14.67%)
>Feat: 12, Missing: 56, Missing ratio: (18.67%)
>Feat: 13, Missing: 104, Missing ratio: (34.67%)
>Feat: 14, Missing: 106, Missing ratio: (35.33%)
>Feat: 15, Missing: 247, Missing ratio: (82.33%)
>Feat: 16, Missing: 102, Missing ratio: (34.00%)
>Feat: 17, Missing: 118, Missing ratio: (39.33%)
>Feat: 18, Missing: 29, Missing ratio: (9.67%)
>Feat: 19, Missing: 33, Missing ratio: (11.00%)
>Feat: 20, Missing: 165, Missing ratio: (55.00%)
>Feat: 21, Missing: 198, Missing ratio: (66.00%)
>Feat: 22, Missing: 1, Missing ratio: (0.33%)
KNNImputer before Missing: 1605
KNNImputer after Missing: 0

Шаг 5: На основе обучения модели конвейера и визуализации

Что такое Pipeline, здесь я напрямую перевожу это в конвейер данных. Любую упорядоченную операцию можно рассматривать как конвейер, например фабричный конвейер, а для моделей машинного обучения — это конвейер данных.
Это означает, что данные проходят через каждый узел в конвейере и после удаления результатов продолжают двигаться вниз по течению. Для нашего примера данные имеют нулевые значения, у нас будет узел KNNImputer для заполнения нулевых значений,
Затем продолжите переход к следующему узлу классификации kNN и, наконец, выведите модель.

results = list()
strategies = [str(i) for i in [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 15, 16, 18, 20, 21]]
for s in strategies:
    # create the modeling pipeline
    pipe = Pipeline(steps=[('imputer', KNNImputer(n_neighbors=int(s))), ('model', KNeighborsClassifier())])
    # 数据多次随机划分取平均得分
    scores = []
    for k in range(20):
        # 得到训练集合和验证集合, 8: 2
        X_train, X_test, y_train, y_test = train_test_split(Xtrans, y, test_size=0.2)
        pipe.fit(X_train, y_train)
        # 验证model
        score = pipe.score(X_test, y_test)
        scores.append(score)
    # 保存results
    results.append(np.array(scores))
    print('>k: %s, Acc Mean: %.3f, Std: %.3f' % (s, np.mean(scores), np.std(scores)))
# print(results)
# plot model performance for comparison
plt.boxplot(results, labels=strategies, showmeans=True)
plt.show()
>k: 1, Acc Mean: 0.800, Std: 0.031
>k: 2, Acc Mean: 0.821, Std: 0.041
>k: 3, Acc Mean: 0.833, Std: 0.053
>k: 4, Acc Mean: 0.824, Std: 0.037
>k: 5, Acc Mean: 0.802, Std: 0.038
>k: 6, Acc Mean: 0.811, Std: 0.030
>k: 7, Acc Mean: 0.797, Std: 0.056
>k: 8, Acc Mean: 0.819, Std: 0.044
>k: 9, Acc Mean: 0.820, Std: 0.032
>k: 10, Acc Mean: 0.815, Std: 0.046
>k: 15, Acc Mean: 0.818, Std: 0.037
>k: 16, Acc Mean: 0.811, Std: 0.048
>k: 18, Acc Mean: 0.809, Std: 0.043
>k: 20, Acc Mean: 0.810, Std: 0.038
>k: 21, Acc Mean: 0.828, Std: 0.038

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-OOHasALA-1638089238611)(output_42_1.png)]

Шаг 6: Анализ результатов

Наш эксперимент состоит в том, чтобы случайным образом разделить данные 20 раз для каждого значения k. Судя по приведенному выше рисунку, в соответствии с увеличением значения k точность нашего теста сначала будет увеличиваться, затем уменьшаться, а затем увеличиваться.
[3, 5] является хорошим значением. Как мы упоминали выше, когда k мало, произойдет переоснащение, а когда k большое, произойдет недооснащение. При встрече с первым нисходящим узлом, В этот момент мы можем
Просто считается, что переобучения не происходит, и можно брать текущее значение k.

2.5 Введение в принцип KNN

Метод k-ближайших соседей - это алгоритм ленивого обучения, который можно использовать для регрессии и классификации. Его основная идея - механизм голосования. Для тестового экземпляра x мы находим k ближайших данных в помеченном наборе обучающих данных, используя Их метки голосуют, задачи классификации голосуют, а задачи регрессии используют методы взвешенного среднего или прямого среднего. В алгоритме knn нам больше всего нужно уделить внимание двум вопросам: выбору значения k и вычислению расстояния.
k в kNN - это гиперпараметр, который нам нужно указать.В общем, это k имеет много общего с данными, и оно выбирается перекрестной проверкой, но рекомендуется использовать перекрестную проверку, k∈[ 2,20], используйте перекрестную проверку, чтобы получить хорошее значение k.

Значение k также может представлять сложность нашей модели. Когда значение k меньше, это означает, что сложность модели становится больше, и ее легче переобучить (переобучение). У нас есть такое предложение, чем больше значение k, тем меньше ошибка оценки обучения, но будет увеличиваться ошибка аппроксимации обучения.


Расчет расстояния/подобия:

Для расчета расстояния между образцами мы обычно используем расстояние Lp. Когда p = 1, это называется манхэттенским расстоянием, когда p = 2, оно называется евклидовым расстоянием, когда p = ∞, оно называется бесконечным расстоянием, что указывает на каждую координату максимальное расстояние , а также включает такие методы, как косинус включенный угол.

Как правило, чаще используется евклидово расстояние, но классификация текста имеет тенденцию использовать косинус для вычисления сходства.

Для двух векторов ( x i , x j ) (x_i,x_j) (xi​,xj​) для расчета обычно используется L p L_p Lp​distance. Предположим, что пространство признаков X X X является n-мерным вещественным векторным пространством R n R^n Rn , где x i , x j ∈ X x_i,x_j \in X xi​,xj​∈X,
xi = ( xi ( 1 ) , xi ( 2 ) , … , xi ( n ) ) x_{i}=\left(x_{i}^{(1)}, x_{i}^{(2)}, \ldots, x_{i}^{(n)}\right) xi​=(xi(1)​,xi(2)​,…,xi(n)​), xj = ( xj ( 1 ) , xj ( 2 ) , … , xj ( n ) ) x_{j}=\left(x_{j}^{(1)}, x_{j}^{(2)}, \ldots, x_{j}^{ (n)}\right) xj​=(xj(1)​,xj(2)​,…,xj(n)​)
x i , x j x_i, x_j xi​, xj​Расстояние L p L_p Lp​определяется как:
L p ( xi , xj ) знак равно ( ∑ l знак равно 1 n ∣ xi ( l ) - xj ( l ) ∣ p ) 1 p L_{p}\left(x_{i}, x_{j}\right)=\ влево (\ sum_ {l = 1} ^ {n} \ left | x_ {i} ^ {(l)} -x_ {j} ^ {(l)} \ right | ^ {p} \ right) ^ {\ frac{1}{p}} Lp​(xi​,xj​)=(l=1∑n​∣∣∣​xi(l)​−xj(l)​∣∣∣​p)p1​

Здесь p ≥ 1 p\geq1 p≥ 1. Когда p = 2 p=2 p=2, это называется евклидовым расстоянием:
L 2 ( xi , xj ) знак равно ( ∑ л знак равно 1 п ∣ xi ( л ) - xj ( л ) ∣ 2 ) 1 2 L_ {2} \ влево (x_ {i}, x_ {j} \ вправо) = \ влево (\ sum_ {l = 1} ^ {n} \ left | x_ {i} ^ {(l)} -x_ {j} ^ {(l)} \ right | ^ {2} \ right) ^ {\ frac{1}{2}} L2​(xi​,xj​)=(l=1∑n​∣∣∣​xi(l)​−xj(l)​∣∣∣​2)21​

Когда p = 1 p=1 p=1, это называется манхэттенским расстоянием:
L 1 ( xi , xj ) знак равно ∑ l знак равно 1 n ∣ xi ( l ) - xj ( l ) ∣ L_{1}\left(x_{i}, x_{j}\right)=\sum_{l=1 }^{n}\left|x_{i}^{(l)}-x_{j}^{(l)}\right| L1​(xi​,xj​)=l=1∑n​∣∣ ∣​xi(l)​−xj(l)​∣∣∣​
Когда p = ∞ p=\infty p=∞, это называется максимальным расстоянием (infty Distance), которое представляет собой максимальное расстояние каждой координаты:
L п ( xi , xj ) знак равно макс ⁡ ln ∣ xi ( l ) - xj ( l ) ∣ L_ {p} \ left (x_ {i}, x_ {j} \ right) = \ max _ {l} n \ left|x_{i}^{(l)}-x_{j}^{(l)}\right| Lp​(xi​,xj​)=lmax​n∣∣∣​xi(l)​−xj (л)​∣∣∣​