Почему 2, повышенное до x, дает отрицательное значение при увеличении x в numpy? - PullRequest
0 голосов
/ 24 мая 2019

Numpy дает массив, содержащий список из 2, возведенных в натуральные числа в виде отрицательных значений.Как 2, возведенные в положительные числа, такие как 1000, могут быть отрицательными?

У меня есть массив 'x', который мы используем для построения значения оси x от 1 до n.Мы берем x ** (2 ** x), т.е. x повышается до (2 повышается до x) для каждого значения в массиве x и используем его в качестве значения оси y.

Случай 1: Для x ∈ [1,50)

Я использовал приведенный ниже код, и вывод правильный, поскольку на выходе np.power (2, x) нет отрицательных значений.

x = np.array([x for x in range(1, 50)])

print(np.power(2, x))
x2x =  np.power(x, np.power(2, x)) 


plt.plot(x, x, label = 'f(n) = n')
plt.plot(x, x2x, label = 'f(n) = x**(2**x)')

plt.legend()
plt.show()

Выход: No negative values in the output

Ссылка на выход

Случай 2: Для x ∈ [1, 100)

Я использовал приведенный ниже код, и выходные данные имеют отрицательные значения на выходе np.power (2, x) и, следовательно, np.power (x, np.power (2, x))

x = np.array([x for x in range(1, 100)])

print(np.power(2, x))
x2x =  np.power(x, np.power(2, x)) 


plt.plot(x, x, label = 'f(n) = n')
plt.plot(x, x2x, label = 'f(n) = x**(2**x)')

plt.legend()
plt.show()

Выход: Negative values in the output

Ссылка на выход

Если x всегда положительный и неубывающий, а 2 постоянный и положительный, то почему 2 повышаетсяк положительному числу, получающему отрицательный вывод в numpy?

Ответы [ 3 ]

0 голосов
/ 24 мая 2019

Вы должны использовать оператор питания Python (**) для своих целей, поскольку даже изменение numpy dtype на int64 не поможет, если размер превышает 64 бита. В то время как мощный оператор Python удовлетворит вашу цель.

x**(2**x)
0 голосов
/ 24 мая 2019

Есть 3 случая, о которых вы, возможно, задаете вопрос.

Случай 1: Вы просто заботитесь о большинстве значащих цифр

Используйте числа с плавающей запятой.Приведите все в double -точное число с плавающей точкой, и оно должно быть примерно до 10 300 .

>>> 3 ** np.array([2, 10, 50, 100], dtype=np.float)
array([9.00000000e+00, 5.90490000e+04, 7.17897988e+23, 5.15377521e+47])

Если вы превышаете это значение, сохраняйте только логарифм чисели используйте соответствующую математику (добавление logs = умножение, умножение logs = возведение в степень), тогда вы будете в порядке до смехотворно больших чисел.

>>> math.log(3) * 50
54.93061443340549
>>> math.log(3) * 50 == math.log(3 ** 50) == math.log(717897987691852588770249)
True

Случай 2: Вы заботитесь только о минимум значащие цифры

Я думаю, это называется "конечное поле" или математика "Галуа"?Обычно используется в криптографии и других вещах.К сожалению, Numpy, похоже, не имеет функции power / modulo, так что вам нужно накатить свою собственную или попробовать обходной путь (те, которые там работают, только если он не переполняется в одной операции, поэтому может не сработать снова).

>>> [pow(3, n, 2 ** 16 + 1) for n in [2, 10, 50, 100]]  # modulo some random prime
[9, 59049, 12911, 33330]

Случай 3: Вам нужно все цифры

Вы должны использовать математику 'bigint', которую Numpy не предоставляет,Целые числа Python - это легкий выбор.

>>> 3 ** np.array([2, 10, 50, 100], dtype=np.object)
array([9, 59049, 717897987691852588770249,
       515377520732011331036461129765621272702107522001], dtype=object)
0 голосов
/ 24 мая 2019

Целые числа, вероятно, переполнены. 32-разрядные целые числа могут содержать только значения до ~ 2,1b, и если они переполняются, они возвращаются в отрицательные значения.

Настройка dtype=int64 может решить вашу проблему. Если нет, просто используйте числа Python (dtype=object). Они не очень эффективны, но могут хранить столько данных, сколько позволит ваша память.

...