Квадратный корень комплексных чисел в python
Я столкнулся с каким-то запутанным поведением с квадратными корнями комплексных чисел в python. Запуск этого кода:
from cmath import sqrt
a = 0.2
b = 0.2 + 0j
print(sqrt(a / (a - 1)))
print(sqrt(b / (b - 1)))
дает выход
0.5j
-0.5j
Аналогичная ситуация с
print(sqrt(-1 * b))
print(sqrt(-b))
Кажется, эти пары утверждений должны дать тот же ответ?
Ответы
Ответ 1
Оба ответа (+0.5j
и -0.5j
) верны, так как они комплексные сопряжения - то есть действительная часть идентична, а мнимая часть - с перевернутым знаком.
Глядя на код, делает поведение ясным - мнимая часть результата всегда имеет тот же знак, что и мнимая часть ввода, как видно из строк 790 и 793:
r.imag = copysign(d, z.imag);
Так как a/(a-1)
есть 0.25
, что неявно 0.25+0j
, вы получаете положительный результат; b/(b-1)
создает 0.25-0j
(по какой-то причине, не уверен, почему это не приводит к 0.25+0j
tbh), поэтому ваш результат аналогично отрицателен.
EDIT: Этот вопрос содержит полезное обсуждение по той же проблеме.
Ответ 2
Я могу ответить, почему это происходит, но не почему было выбрано поведение.
a/(a - 1)
оценивается до 0,2/-0,8, что составляет -0,25, которое преобразуется в комплексное число на cmath.sqrt
, а
b/(b - 1)
оценивает (0.2 + 0j)/(- 0.8 + 0j), который равен (-0.25-0j), который преобразуется в комплексное число с отрицательной комплексной составляющей.
Для более простого примера,
cmath.sqrt(0j) == 0j
cmath.sqrt(-0j) == -0j