Вы можете использовать sklearns Standardscaler. Он масштабирует ваши данные, чтобы иметь дисперсию 1 и среднее значение 0. Среднее значение 0 эквивалентно сумме 0.
from sklearn.preprocessing import StandardScaler, MinMaxScaler
import numpy as np
rand_numbers = StandardScaler().fit_transform(np.random.rand(100,1, ))
Если вы не хотите использовать sklearn, вы можете стандартизировать с помощьюС другой стороны, формула довольно проста:
rand_numbers = np.random.rand(1000,1, )
rand_numbers = (rand_numbers - np.mean(rand_numbers)) / np.std(rand_numbers)
Проблема здесь заключается в дисперсии 1, которая приводит к числам больше 1 или меньше -1. Для этого вы делите массив на максимальное значение абс.
rand_numbers = rand_numbers*(1/max(abs(rand_numbers)))
Теперь у вас есть массив со значениями от -1 до 1 с суммой, действительно близкой к нулю.
print(sum(rand_numbers))
print(min(rand_numbers))
print(max(rand_numbers))
Вывод:
[-1.51822999e-14]
[-0.99356294]
[1.]
То, что у вас будет с этим решением, всегда будет либо один 1, либо один -1 в ваших данных. Если вы хотите избежать этого, вы можете добавить положительный случайный коэффициент к делению через максимальный абс. rand_numbers*(1/(max(abs(rand_numbers))+randomfactor))
Редактировать
Как упомянул @KarlKnechtel, деление на стандартное отклонение является избыточным с делением на максимальное абсолютное значение.
Вышесказанное можно сделать просто:
rand_numbers = np.random.rand(100000,1, )
rand_numbers = rand_numbers - np.mean(rand_numbers)
rand_numbers = rand_numbers / max(abs(rand_numbers))