Вопрос или проблема
Я пытаюсь использовать SVR для предсказания определенной характеристики. Я создаю модель с помощью следующего кода:
from sklearn.svm import SVR
from sklearn.preprocessing import StandardScaler
X = data
# это переменная результата
y = data.iloc[:, 10].values
sc_X = StandardScaler()
sc_y = StandardScaler()
X2 = sc_X.fit_transform(X)
y = sc_y.fit_transform(y.reshape(-1, 1))
# my_custom_kernel смотрит на определенные столбцы X2 / отмасштабированные данные
my_regressor = SVR(kernel=my_custom_kernel)
my_regressor = regressor.fit(X2, y)
После создания модели я хочу протестировать ее, чтобы увидеть, хорошо ли предсказание. Первое, что делает код, это масштабирует строку, которую я хочу протестировать, используя тот же масштабатор, что и выше (sc_X
). Затем я пытаюсь обратить масштабирование результата предсказания (используя sc_y
). В процессе я получаю ошибки типов данных. Вот код:
line1 = X.iloc[0].as_matrix().reshape(1, -1)
line1_scaled = sc_X.fit_transform(line1)
res = regressor.predict (line1_scaled)
pred_line1 = sc_y.inverse_transform (res) # Ошибка, скорее всего, здесь
Ошибка:
ValueError: non-broadcastable output operand with shape (1,) doesn't match the broadcast shape (24,)
Спасибо.
Во-первых, я не уверен, почему вы хотите масштабировать значение “Y” вообще? Обратная трансформация применяется для обратного масштабирования характеристик X в основном.
https://scikit-learn.org/stable/modules/generated/sklearn.preprocessing.MinMaxScaler.html#sklearn.preprocessing.MinMaxScaler.inverse_transform
Во-вторых, вы сейчас передаете только 1 столбец X для предсказания, и ваш sc_y
запоминает форму, которую вы передали ему ранее. Ваша ошибка говорит вам о различии также. Один имеет (24,), а другой (1,).
Чтобы ответить на ваш вопрос:
- Во-первых, при разделении данных на X и Y вам необходимо удалить целевой столбец при выборе X и выбрать только целевой столбец в качестве Y.
- Во-вторых, вам не нужно масштабировать ваш целевой столбец. Но если в нем есть выбросы, вы можете использовать Box-Cox или log1e или sqrt, чтобы преобразовать ваш целевой столбец в гауссовский формат. Но при предсказании убедитесь, что вы вернули данные в их оригинальный формат.
- Наконец, о ошибке: это похоже на несоответствие количества столбцов в обучающем и тестовом наборах. Убедитесь, что у вас одинаковое количество столбцов для предсказания.
- Общий/Лучший способ сделать масштабирование:
from sklearn.preprocessing import StandardScaler
X_train = df_train.drop('target', axis = 1)
y_train = df_train['target']
X_test = df_test # Предполагая, что в тестовом наборе нет целевого столбца
sc = StandardScaler()
X_train = sc.fit_transform(X_train)
X_test = sc.transform(X_test)
# ===== Здесь ваша модель SVR ===== #
predict = model.predict(X_test)
Надеюсь, это сработает хорошо.
Ответ или решение
Масштабирование и обратное масштабирование данных для предсказания на основе SVR
Введение
Оценка качества моделей машинного обучения, таких как Регрессия с Опорными Векторами (SVR), требует правильной подготовки данных, включая масштабирование и обратное масштабирование. В данном руководстве мы рассмотрим подходы к масштабированию данных, а также решение проблем, связанных с ошибками при предсказании.
Проблема масштабирования
Масштабирование данных является критически важным шагом на этапе подготовки данных, особенно для алгоритмов, чувствительных к масштабам, таких как SVR. В вашем коде используется StandardScaler
для стандартизации как входных данных (X
), так и целевой переменной (y
). Однако, существует несколько важных нюансов, о которых стоит упомянуть:
-
Масштабирование целевой переменной (
y
): Обычно целевая переменная не требует масштабирования, если нет строгой необходимости (например, при наличии выбросов). В вашем случае рекомендуется использовать методы трансформации, такие как логарифмическая или корневая, чтобы корректировать распределение. -
Использование fit_transform и transform: В приведенном вами коде при тестировании модели используется
fit_transform
для новых данных, что может вызвать несоответствия при обратном масштабировании. Вместо этого, следует использоватьtransform
, чтобы избежать повторного обучения скейлера.
Ошибки при обратном масштабировании
Ваш код привел к ошибке:
ValueError: non-broadcastable output operand with shape (1,) doesn't match the broadcast shape (24,)
Эта ошибка означает, что вы пытаетесь выполнить операцию над массивами с несовместимыми размерами. Конкретно, вы передаете одномерный массив в функцию inverse_transform
, в то время как скейлер ожидает массив в виде двумерной матрицы.
Правильный подход к масштабированию
Чтобы избежать подобных ошибок, следует придерживаться следующей структуры кода:
from sklearn.svm import SVR
from sklearn.preprocessing import StandardScaler
# Разделение на переменные X и y
X = data.drop(columns=['target']) # замените 'target' на ваше название столбца
y = data['target'].values # снова замените 'target' на ваше название столбца
sc_X = StandardScaler()
sc_y = StandardScaler()
# Масштабирование данных
X_scaled = sc_X.fit_transform(X)
y_scaled = sc_y.fit_transform(y.reshape(-1, 1)).flatten() # Делаем y одномерным
# Обучение модели
my_regressor = SVR(kernel=my_custom_kernel)
my_regressor.fit(X_scaled, y_scaled)
# Тестирование модели
line1 = X.iloc[0].values.reshape(1, -1) # Извлечение одной строки для предсказания
line1_scaled = sc_X.transform(line1) # Используем transform вместо fit_transform
res = my_regressor.predict(line1_scaled)
pred_line1 = sc_y.inverse_transform(res.reshape(-1, 1)) # Приведение к двумерному виду для обратного масштабирования
Заключение
Надлежащая обработка данных, включая корректное масштабирование и обратное масштабирование, играет важную роль в успешном предсказании при использовании моделей, таких как SVR. Ключевыми моментами являются использование методов fit и transform, правильное масштабирование целевой переменной и соответствие форматов данных. Используя предложенные рекомендации, вы сможете успешно подготовить данные и избежать ошибок в процессе предсказания.