==== boost::math, complex number algorithms ====
Marcin Klocek, T-RTM
----
=== Wstęp ===
Biblioteka boost::math zawiera sześć funkcji operujących na liczbach zespolonych. Są to odwrotne funkcje trygonometryczne, które zostały zaprojektowane w taki sposób, aby zapewnić zgodność z funkcjami trygonometrycznymi dla liczb zespolonych dostępnymi w C++. Jednocześnie funkcje te zwracają poprawne wyniki nawet dla krańcowych wartości parametru. Maksymalny błąd względny metody zastosowanej do wyliczania tych funkcji szacowany jest na 10-9.
----
=== Przegląd odwrotnych funkcji trygonometrycznych ===
== Sinus ==
Plik nagłówkowy:
#include
Postać funkcji:
template
std::complex asin(const std::complex& z);
Wzór:
{{boost_asin.png}}
== Cosinus ==
Plik nagłówkowy:
#include
Postać funkcji:
template
std::complex acos(const std::complex& z);
Wzór:
{{boost_acos.png}}
== Tangens ==
Plik nagłówkowy:
#include
Postać funkcji:
template
std::complex atan(const std::complex& z);
Wzór:
{{boost_atan.png}}
== Sinus hiperboliczny ==
Plik nagłówkowy:
#include
Postać funkcji:
template
std::complex asinh(const std::complex& z);
Wzór:
{{boost_asinh.png}}
== Cosinus hiperboliczny ==
Plik nagłówkowy:
#include
Postać funkcji:
template
std::complex acosh(const std::complex& z);
Wzór:
{{boost_acosh.png}}
== Tangens hiperboliczny ==
Plik nagłówkowy:
#include
Postać funkcji:
template
std::complex atanh(const std::complex& z);
Wzór:
{{boost_atanh.png}}
----
=== Przykładowy program ===
Poniższy program oblicza wartość funkcji trygonometrycznych dla danej liczby zespolonej korzystając z funkcji dostępnych w C++. Wynik jest następnie odwracany przy wykorzystaniu frunkcji z boost::math. Na ekranie wyświetlane są wyniki, a także względny błąd obliczenia części rzeczywistej i urojonej.\\
{{complex_boost_example.cpp}}:
/*****************************************************************
* Program testujacy odwrotne funkcje trygonometryczne dla liczb *
* zespolonych zawarte w bibliotece boost::math pod katem ich *
* zgodnosci z funkcjami trygonometrycznymi w bibliotece std. *
* Dodatkowo wyswietlane sa wzgledne bledy okreslenia czesci *
* rzeczywistej i urojonej. *
* *
* Ze wzgledu na okresowosc funkcji trygonometrycznych nalezy *
* uzywac wartosci z przedzialu <-pi/2; pi/2>. *
*****************************************************************/
#include
#include
#include
#include
#include
#include
#include
int main() {
double re;
double im;
char sign;
std::cout << "Podaj liczbe zespolona w postaci X + jY: ";
std::cin >> re;
std::cin >> sign; //zebranie znaku
getchar(); //zebranie spacji
getchar(); //zebranie 'j'
std::cin >> im;
getchar();
std::cout << std::endl;
if (sign == '-')
im = -im;
std::complex c1 (re, im); //liczba pierwotna
std::complex cf; //wynik operacji z biblioteki std
std::complex cb; //wynik operacji odwrotnej z boost::math
std::complex dc; //blad obliczeniowy, zdefiniowany jako cb - c1
//sinus
cf = std::sin(c1);
cb = boost::math::asin(cf);
dc = cb - c1;
std::cout << "Liczba pierwotna: " << c1 << std::endl <<
"std::sin: " << cf << std::endl <<
"boost::math::asin: " << cb << std::endl;
std::cout << "Blad wzgledny okreslenia czesci rzeczywistej: " << dc.real() * 100 / c1.real() << "%" << std::endl <<
"Blad wzgledny okreslenia czesci urojonej: " << dc.imag() * 100 / c1.imag() << "%" << std::endl;
getchar();
//cosinus
cf = std::cos(c1);
cb = boost::math::acos(cf);
dc = cb - c1;
std::cout << "Liczba pierwotna: " << c1 << std::endl <<
"std::cos: " << cf << std::endl <<
"boost::math::acos: " << cb << std::endl;
std::cout << "Blad wzgledny okreslenia czesci rzeczywistej: " << dc.real() * 100 / c1.real() << "%" << std::endl <<
"Blad wzgledny okreslenia czesci urojonej: " << dc.imag() * 100 / c1.imag() << "%" << std::endl;
getchar();
//tangens
cf = std::tan(c1);
cb = boost::math::atan(cf);
dc = cb - c1;
std::cout << "Liczba pierwotna: " << c1 << std::endl <<
"std::tan: " << cf << std::endl <<
"boost::math::atan: " << cb << std::endl;
std::cout << "Blad wzgledny okreslenia czesci rzeczywistej: " << dc.real() * 100 / c1.real() << "%" << std::endl <<
"Blad wzgledny okreslenia czesci urojonej: " << dc.imag() * 100 / c1.imag() << "%" << std::endl;
getchar();
//sinus hiperboliczny
cf = std::sinh(c1);
cb = boost::math::asinh(cf);
dc = cb - c1;
std::cout << "Liczba pierwotna: " << c1 << std::endl <<
"std::sinh: " << cf << std::endl <<
"boost::math::asinh: " << cb << std::endl;
std::cout << "Blad wzgledny okreslenia czesci rzeczywistej: " << dc.real() * 100 / c1.real() << "%" << std::endl <<
"Blad wzgledny okreslenia czesci urojonej: " << dc.imag() * 100 / c1.imag() << "%" << std::endl;
getchar();
//cosinus hiperboliczny
cf = std::cosh(c1);
cb = boost::math::acosh(cf);
dc = cb - c1;
std::cout << "Liczba pierwotna: " << c1 << std::endl <<
"std::cosh: " << cf << std::endl <<
"boost::math::acosh: " << cb << std::endl;
std::cout << "Blad wzgledny okreslenia czesci rzeczywistej: " << dc.real() * 100 / c1.real() << "%" << std::endl <<
"Blad wzgledny okreslenia czesci urojonej: " << dc.imag() * 100 / c1.imag() << "%" << std::endl;
getchar();
//tangens hiperboliczny
cf = std::tanh(c1);
cb = boost::math::atanh(cf);
dc = cb - c1;
std::cout << "Liczba pierwotna: " << c1 << std::endl <<
"std::tanh: " << cf << std::endl <<
"boost::math::atanh: " << cb << std::endl;
std::cout << "Blad wzgledny okreslenia czesci rzeczywistej: " << dc.real() * 100 / c1.real() << "%" << std::endl <<
"Blad wzgledny okreslenia czesci urojonej: " << dc.imag() * 100 / c1.imag() << "%" << std::endl;
getchar();
return 0;
}