Как нормализовать 2-мерный массив numpy в python менее подробный?
Учитывая 3-кратный 3-мерный массив
a = numpy.arange(0,27,3).reshape(3,3)
# array([[ 0, 3, 6],
# [ 9, 12, 15],
# [18, 21, 24]])
Чтобы нормализовать строки двумерного массива, я думал о
row_sums = a.sum(axis=1) # array([ 9, 36, 63])
new_matrix = numpy.zeros((3,3))
for i, (row, row_sum) in enumerate(zip(a, row_sums)):
new_matrix[i,:] = row / row_sum
Должен быть лучший способ, не так ли?
Возможно, чтобы очистить: по нормализации я имею в виду, что сумма записей в строке должна быть одной. Но я думаю, что это будет понятно большинству людей.
Ответы
Ответ 1
Вещание действительно полезно для этого:
row_sums = a.sum(axis=1)
new_matrix = a / row_sums[:, numpy.newaxis]
row_sums[:, numpy.newaxis]
изменяет row_sums с (3,)
на (3, 1)
. Когда вы выполняете a / b
, a
и b
транслируются друг против друга.
Вы можете узнать больше о трансляции здесь или даже лучше здесь.
Ответ 2
Scikit-learn имеет функцию нормализации, которая позволяет применять различные нормализации. "Сделать сумму до 1" является нормой L1, и сделать это:
from sklearn.preprocessing import normalize
matrix = numpy.arange(0,27,3).reshape(3,3).astype(numpy.float64)
#array([[ 0., 3., 6.],
# [ 9., 12., 15.],
# [ 18., 21., 24.]])
normed_matrix = normalize(matrix, axis=1, norm='l1')
#[[ 0. 0.33333333 0.66666667]
#[ 0.25 0.33333333 0.41666667]
#[ 0.28571429 0.33333333 0.38095238]]
Теперь ваши строки будут суммироваться до 1.
Ответ 3
Я думаю, что это должно сработать,
a = numpy.arange(0,27.,3).reshape(3,3)
a /= a.sum(axis=1)[:,numpy.newaxis]
Ответ 4
Если вы пытаетесь нормализовать каждую строку так, чтобы ее величина была одной (т.е. длина единицы строки равна единице или сумма квадрата каждого элемента в строке равна единице):
import numpy as np
a = np.arange(0,27,3).reshape(3,3)
result = a / np.linalg.norm(a, axis=-1)[:, np.newaxis]
# array([[ 0. , 0.4472136 , 0.89442719],
# [ 0.42426407, 0.56568542, 0.70710678],
# [ 0.49153915, 0.57346234, 0.65538554]])
Проверка:
np.sum( result**2, axis=-1 )
# array([ 1., 1., 1.])
Ответ 5
похоже, что это также работает
def normalizeRows(M):
row_sums = M.sum(axis=1)
return M / row_sums
Ответ 6
Или используя лямбда-функцию, например
>>> vec = np.arange(0,27,3).reshape(3,3)
>>> import numpy as np
>>> norm_vec = map(lambda row: row/np.linalg.norm(row), vec)
каждый вектор vec будет иметь единичную норму.
Ответ 7
Вы также можете использовать перенос матрицы:
(a.T / row_sums).T
Ответ 8
Я думаю, что вы можете нормализовать сумму элементов строки до 1 следующим образом: new_matrix = a / a.sum(axis=1, keepdims=1)
.
А нормализацию столбца можно выполнить с помощью new_matrix = a / a.sum(axis=0, keepdims=1)
. Надеюсь, что это может помочь.
Ответ 9
normed_matrix = normalize(input_data, axis=1, norm='l1')
print(normed_matrix)
где input_data - имя вашего 2D-массива