Скорость для различных ядер в SVM scikit-learn

Вопрос или проблема

Я использую scikit-learn в Python для создания моделей, пробуя разные ядра. Я был удивлён, увидев, что RBF обучается менее чем за секунду, тогда как линейная модель заняла минуту, а полиномиальная — часы. Может кто-то объяснить, почему это происходит?

Мой код:

import numpy as np
from sklearn.svm import SVR
import matplotlib.pyplot as plt
from sklearn.metrics 
import mean_squared_error, r2_score
f = open(datafile)
X = np.empty([0,1], dtype = int)
y = np.array([])
for i in range(100):
    my_lines = f.readline().split(" ")
    t = np.array([[int(my_lines[0])]])
    n = np.array([int(my_lines[1])])
    X = np.concatenate((X, t), axis =0 )
    y = np.concatenate((y, np.array([int(my_lines[1])])), axis = 0)
f.close()
svr_rbf = SVR(kernel="rbf", C=1e3, gamma=0.1)
svr_lin = SVR(kernel="linear", C=1e3)
svr_poly = SVR(kernel="poly", C=1e3, degree=3)
svr_rbf.fit(X, y)
svr_lin.fit(X, y)
svr_poly.fit(X, y)

Данные:

0 22
1 23
2 23
3 23
4 25
5 24
6 25
7 26
8 26
9 30
10 29
11 29
12 30
13 30
14 30
15 31
16 29
17 28
18 29
19 31
20 30
21 30
22 31
23 31
24 30
25 31
26 31
27 30
28 29
29 31
30 33
31 31
32 32
33 30
34 30
35 30
36 29
37 30
38 29
39 29
40 27
41 28
42 28
43 27
44 27
45 28
46 28
47 29
48 29
49 28
50 28
51 29
52 27
53 27
54 28
55 28
56 28
57 30
58 32
59 31
60 30
61 28
62 28
63 30
64 27
65 27
66 28
67 27
68 29
69 33
70 39
71 35
72 34
73 29
74 30
75 28
76 28
77 29
78 27
79 26
80 25
81 17
82 0
83 0
84 29
85 21
86 20
87 18
88 19
89 19
90 19
91 18
92 17
93 18
94 20
95 19
96 20
97 19
98 18
99 18

Один из способов ускорить ваш код — стандартизировать признаки, убрав среднее и масштабировав к единичной дисперсии.

from sklearn.preprocessing import StandardScaler

scaler = StandardScaler()
X = scaler.fit_transform(X.reshape(-1, 1))
y = scaler.fit_transform(y.reshape(-1, 1))

После того, как я стандартизировал данные, каждая модель обучилась за менее чем 500 мс.

Методы опорных векторов (SVM) должны вычислять расстояние между каждыми данными. Стандартизированные числа упрощают и ускоряют вычисления.

Ответ или решение

Ваша ситуация с использованием модели SVM в библиотеке scikit-learn и различиями по времени для разных ядер (kernels) интересна и вполне объяснимая. Попробуем разобраться в причинах этих различий, а также в том, как улучшить производительность.

Причины различий во времени обучения

  1. Тип ядра:

    • Линейное ядро: При использовании линейного ядра (kernel="linear"), SVM решает задачу с помощью простой линейной модели. Он полагается на вычисление весов для линейного уравнения и, следовательно, требует больше времени на обработку большого количества данных из-за человеческого вмешательства в составление гиперпараметров.
    • Ядро RBF: Ядро радиальной базисной функции (RBF) представляет собойGaussian (Гауссовское) ядро, что позволяет SVM эффективно находить сложные границы принятия решений. Однако для RBF не требуется существенное пересчитывание весов для фильтрации пространства, что может привести к более быстрому обучению при определённых условиях.
    • Полиномиальное ядро: При использовании полиномиального ядра (kernel="poly"), вычисления становятся более сложными, так как алгоритм должен учитывать все возможные полиномиальные комбинации входных переменных. Это значительно увеличивает вычислительные ресурсы и время, особенно при большой размерности и числе образцов.
  2. Выравнивание данных:

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

Рекомендации по улучшению производительности

Как правильно заметили, одним из простых способов ускорить обучение SVM является стандартизация данных. Стандартизация помогает упростить вычисления и позволяет алгоритму более эффективно находить лучшие параметры.

Вы можете использовать StandardScaler из библиотеки scikit-learn, как вы уже предложили, чтобы стандартизировать и масштабировать ваши данные:

from sklearn.preprocessing import StandardScaler

scaler = StandardScaler()
X = scaler.fit_transform(X.reshape(-1, 1))
y = scaler.fit_transform(y.reshape(-1, 1))

После стандартных преобразований время обучения для всех подходов к модели станет значительно короче, и вы заметите, что каждая модель обучается менее чем за 500 миллисекунд.

Заключение

Таким образом, разница во времени, необходимом для обучения моделей SVM с разными ядрами, может быть объяснена сложностью вычислений, характерной для каждого ядра. Стандартизация данных — это суть в том, как можно сократить время обработки. Эффективные алгоритмы, такие как SVM, выигрывают от упрощения вычислений через масштабирование и стандартизацию. Используя эти подходы, вы сможете добиться значительно лучшей производительности при работе с вашими данными.

Оцените материал
Добавить комментарий

Капча загружается...