C++ умножение комплексных чисел

Если у меня есть (1+i)^2, ответ должен быть 2i

Но если я сделаю

std::complex<double> i = sqrt(1), one = 1;
cout << pow(one+i,2) << endl;

Выводит (4,0)

2 ответа

Решение

Вы инициализируете i в sqrt(1) в то время как вы, вероятно, думали о sqrt(-1), Как таковой он будет оценен как double выражение (после -1 преобразуется в удвоенное в качестве ближайшего соответствия sqrtсм. комментарий Майка для полной последовательности), которая согласно cplusplus.com генерирует ошибку домена для отрицательных аргументов.

Вместо этого вы можете инициализировать i как:

std::complex<double> i(0,1);

В качестве альтернативы вы можете использовать комплексное число в качестве аргумента sqrt как описано в этом ответе, или как указано в комментариях Potatoswatter в комментариях 1.i с C++14 (если у вас есть компилятор и стандартная библиотека, которая поддерживает пользовательские литералы для стандартных типов библиотек, часть 2).

math.h заголовок в C++ обеспечивает следующие перегрузки sqrt:

auto sqrt( float arg ) -> float;
auto sqrt( double arg ) -> double;
auto sqrt( long double arg ) -> long double;
auto sqrt( Integral arg ) -> double;    // C++11 and later

где Integral обозначает любой целочисленный тип (это набор перегрузок или шаблон функции).

<complex> заголовок дополнительно определяет эту перегрузку:

template< class T >
auto sqrt( complex<T> const& x ) -> complex<T>;

Там также перегрузка для valarray, но здесь это не актуально.

Когда вы используете -1 в качестве фактического аргумента, как

sqrt( -1 )

прямое соответствие типа аргумента, перегрузка с Integral аргумент, лучше всего подходит, и эта перегрузка возвращает double,

Там нет никакого способа представить математическое я как double значение. Таким образом, значение, которое вы получаете, является значением, определяемым реализацией (если ваша реализация C++ double тип поддерживает NaN, а не число, это может быть NaN); "Является ли целочисленное выражение errno приобретает ценность EDOM определяется реализацией "в соответствии с C99 §7.12.1/2. Чтобы избежать этого, вы можете убедиться, что -1 преобразуется в аргумент типа complex<double>, сказать:

sqrt( complex<double>( -1 ) )

С компиляторами, которые я пробовал, это дает тот же результат, что и запись

complex<double>( 0, 1 )

который представляет собой математический я, квадратный корень из минус 1.

Другие вопросы по тегам