Python numpy ValueError: операнды не могут транслироваться вместе с фигурами
У numpy у меня есть два "массива", X
- это (m,n)
а y
- это вектор (n,1)
с помощью
X*y
Я получаю ошибку
ValueError: operands could not be broadcast together with shapes (97,2) (2,1)
Когда (97,2)x(2,1)
явно является законной матричной операцией и должен дать мне (97,1)
вектор
РЕДАКТИРОВАТЬ:
Я исправил это с помощью X.dot(y)
но оригинальный вопрос все еще остается.
Ответы
Ответ 1
dot
- это матричное умножение, но *
делает что-то еще.
У нас есть два массива:
-
X
, форма (97,2) -
y
, форма (2,1)
С массивами Numpy, операция
X * y
выполняется поэлементно, но одно или оба значения можно расширить в одно или несколько измерений, чтобы сделать их совместимыми. Эта операция называется трансляцией. Размеры, в которых размер равен 1 или отсутствуют, могут использоваться при трансляции.
В приведенном выше примере размеры несовместимы, потому что:
97 2
2 1
Здесь есть противоречивые числа в первом измерении (97 и 2). Это то, на что жалуется ValueError выше. Второе измерение было бы в порядке, так как число 1 не конфликтует ни с чем.
Для получения дополнительной информации о правилах вещания: http://docs.scipy.org/doc/numpy/user/basics.broadcasting.html
(Обратите внимание, что если X
и y
имеют тип numpy.matrix
, то звездочку можно использовать как умножение матриц. Я рекомендую держаться подальше от numpy.matrix
, это может усложнить нечто большее, чем упростить.)
Ваши массивы должны быть в порядке с numpy.dot
; Если вы получили ошибку в numpy.dot
, у вас должна быть другая ошибка. Если фигуры неправильны для numpy.dot
, вы получите другое исключение:
ValueError: matrices are not aligned
Если вы все еще получаете эту ошибку, пожалуйста, опубликуйте минимальный пример проблемы. Пример умножения с массивами, подобными вашему, успешен:
In [1]: import numpy
In [2]: numpy.dot(numpy.ones([97, 2]), numpy.ones([2, 1])).shape
Out[2]: (97, 1)
Ответ 2
Per Wes McKinney Python для анализа данных
Правило широковещания: два массива являются совместимыми для широковещания, если для каждого конечного измерения (то есть, начиная с конца) длины осей совпадают или если любая из длин равна 1. В этом случае широковещание выполняется по отсутствующей и/или длине 1 размеры.
Другими словами, если вы пытаетесь умножить две матрицы (в смысле линейной алгебры), вам нужен X.dot(y)
но если вы пытаетесь транслировать скаляры из матрицы y
на X
то вам нужно выполнить X * yT
.
Пример:
>>> import numpy as np
>>>
>>> X = np.arange(8).reshape(4, 2)
>>> y = np.arange(2).reshape(1, 2) # create a 1x2 matrix
>>> X * y
array([[0,1],
[0,3],
[0,5],
[0,7]])
Ответ 3
Возможно, что ошибка возникла не в точечном произведении, а после. Например попробуйте это
a = np.random.randn(12,1)
b = np.random.randn(1,5)
c = np.random.randn(5,12)
d = np.dot(a,b) * c
np.dot(a, b) будет в порядке; однако np.dot(a, b) * c явно неверен (12x1 X 1x5 = 12x5, который не может умножаться на элементы 5x12), но numpy даст вам
ValueError: operands could not be broadcast together with shapes (12,1) (1,5)
Ошибка вводит в заблуждение; однако есть проблема в этой линии.
Ответ 4
Используйте np.mat(x) * np.mat(y), это сработает.