Różnice między wybraną wersją a wersją aktualną.
Both sides previous revision Previous revision Next revision | Previous revision Next revision Both sides next revision | ||
liczby_zespolone_complex [2008/11/09 15:10] lromanow |
liczby_zespolone_complex [2008/11/09 19:52] lromanow |
||
---|---|---|---|
Linia 1: | Linia 1: | ||
- | ==== Liczby zespolone <complex> ==== | + | ====== Liczby zespolone <complex> ====== |
- | The class complex is a template class, used to create objects for representing and manipulating complex numbers. The operations defined on complex numbers allow them to be freely intermixed with the other numeric types available in the C++ language, thereby permitting numeric software to be easily and naturally expressed. | + | |
+ | Klasa szablonowa ''**complex**'' służy do reprezentacji i manipulacji liczbami zespolonymi. Operacje zdefiniowane na liczbach zespolonych pozwalają na swobodne mieszanie obiektów tej klasy z wbudowanymi typami numerycznymi. Należy zauważyć, że większość operacji wykonywanych na obiektach tej klasy to zwykłe funkcje. Wyjątkami są metody ''real()'' i ''imag()'' należące do klasy ''**complex**''. | ||
+ | |||
+ | ===== Deklaracja liczb zespolonych ===== | ||
+ | |||
+ | Argument szablonu określa typ związany z wartościami części rzeczywistej i urojonej obiektu. Ten argument musi być jednym z trzech dostępnych typów zmiennoprzecinkowych ''**float**'', ''**double**'' lub ''**long double**''. | ||
+ | |||
+ | Dostępne są cztery konstruktory. Konstruktor bezparametrowy inicjalizuje obie części liczby zespolonej wartością zero. Konstruktor jednoargumentowy incjalizuje wartością parametru część rzeczywistą i zeruje urojoną. Konstruktor dwuargumentowy inicjalizuje obie części liczby zespolonej. Ostatecznie, konstruktor kopiujący pozwala inicjalizować obiekt wartościami innego dostępnego obiektu klasy. | ||
+ | |||
+ | <code cpp> | ||
+ | complex<double> cplx_one; // wartość 0 + 0i | ||
+ | complex<double> cplx_two(3.14); // wartość 3.14 + 0i | ||
+ | complex<double> cplx_three(1.5, 3.14) // wartość 1.5 + 3.14i | ||
+ | complex<double> cplx_four(cplx_two); // wartość również 3.14 + 0i | ||
+ | </code> | ||
+ | |||
+ | Liczbie zespolonej ''**complex**'' można przypisać wartość innej liczby zespolonej. Ponieważ konstruktor jednoargumentowy jest również wykorzystywany jako operator konwersji, można również przypisać liczbie zespolonej wartość rzeczywistą. | ||
+ | |||
+ | <code cpp> | ||
+ | cplx_one = cplx_three; // staje się 1.5 + 3.14i | ||
+ | cplx_three = 2.17; // staje się 2.17 + 0i | ||
+ | </code> | ||
+ | |||
+ | Funkcja ''polar()'' może służyć do konstrukcji liczby zespolonej dla danego modułu i fazy kąta. | ||
+ | |||
+ | <code cpp> | ||
+ | cplx_four = polar(5.6, 1.8); | ||
+ | </code> | ||
+ | |||
+ | Wartość sprzężona powstaje z użyciem funkcji ''conj()''. | ||
+ | |||
+ | <code cpp> | ||
+ | complex<double> cplx_five = conj(cplx_four); | ||
+ | </code> | ||
+ | |||
+ | ===== Dostęp do wartości liczby zespolonej ===== | ||
+ | |||
+ | Metody klasy ''**complex**'' ''real()'' i ''imag()'' zwracają wartości odpowiednio części rzeczywistej i urojonej liczby zespolonej. Funkcje te można również wywołać jako zwykłe funkcje z obiektem klasy ''**complex**'' jako argument. | ||
+ | |||
+ | <code cpp> | ||
+ | cout << cplx_one.real() << "+" << cplx_one.imag() << "i" << endl; | ||
+ | cout << real(cplx_one) << "+" << imag(cplx_one) << "i" << endl; | ||
+ | </code> | ||
+ | |||
+ | ===== Operatory artmetyczne ===== | ||
+ | |||
+ | Operatory artmetyczne ''+'', ''-'', ''*'' oraz ''/'' mogą być używane zgodnie z przyjętą konwencją. Wszystkie przyjmują jako argumenty albo dwie liczby zespolone albo liczbę zespoloną i wartość rzeczywistą. Ponadto zdefiniowane są dla każdego z nich operatory przypisania. | ||
+ | |||
+ | <code cpp> | ||
+ | cout << cplx_one + cplx_two << endl; // wartość 4.64+3.14i | ||
+ | cout << cplx_one - 3.14 << endl; // wartość -1.64+3.14i | ||
+ | cout << 2.75 * cplx_two << endl; // wartość 8.635+0i | ||
+ | cout << (cplx_one += cplx_three / 2.0) << endl; // wartość 2.585+3.14i | ||
+ | </code> | ||
+ | |||
+ | Operatory jednoargumentowe ''+'' i ''-'' również można używać. | ||
+ | |||
+ | <code cpp> | ||
+ | cout << -cplx_one << endl; // wartość -2.585-3.14i | ||
+ | </code> | ||
+ | |||
+ | ===== Porównywanie wartości ===== | ||
+ | |||
+ | Dwie liczby zespolone ''**complex**'' mogą być przetestowane na równość lub nierówność wykorzystując operatory ''=='' i ''!=''. Dwie wartości są równe, gdy odpowiadające sobie części liczby są sobie równe. | ||
+ | |||
+ | <code cpp> | ||
+ | cout << (cplx_one == cplx_three) << endl; // wartość 0 (fałsz) | ||
+ | cout << (cplx_one != cplx_three) << endl; // wartość 1 (prawda) | ||
+ | </code> | ||
+ | |||
+ | Liczby zespolone nie mogą być porównywane za pomocą innych operatorów, niedostępne są operatory porządkujące. | ||
+ | |||
+ | ===== Strumienie I/O ===== | ||
+ | |||
+ | Liczby zespolone klasy ''**complex**'' mogą być pisane do strumienia bądź z niego czytane wykorzystując przyjętą konwencję dla strumieni I/O. Wartość pisana jest do strumienia w nawiasach jako ''(u,v)''. Wartość jest czytana ze strumienia jako dwie wartości numeryczne oddzielone przecinkiem i otoczone nawiasami. | ||
+ | |||
+ | ===== Wartość normalna i moduł ===== | ||
+ | |||
+ | Funkcja ''norm()'' zwraca normę liczby zespolonej, która odpowiada sumie kwadratów części rzeczywistej i urojonej. Funkcja ''abs()'' zwraca moduł, który jest pierwiastkiem kwadratowym normy liczby zespolonej. | ||
+ | |||
+ | <code cpp> | ||
+ | cout << norm(cplx_two) << endl; | ||
+ | cout << abs(cplx_two) << endl; | ||
+ | </code> | ||
+ | |||
+ | Kąt fazowy liczby zespolonej można uzyskać za pomocą funkcji ''arg()''. | ||
+ | |||
+ | <code cpp> | ||
+ | cout << cplx_four << " w postaci biegunowej wynosi " | ||
+ | << abs(cplx_four) << "e^" << arg(cplx_four) << "i"<< endl; | ||
+ | </code> | ||
+ | |||
+ | ===== Funkcje trygonometryczne ===== | ||
+ | |||
+ | Funkcje tryugonometryczne zdefiniowane dla typów zmiennoprzecinkowych zostały rozszerzone dla liczb zespolonych. Dotyczy to funkcji ''sin()'', ''cos()'', ''tan()'', ''sinh()'', ''cosh()'' i ''tanh()''. Każda z nich bierze jako argument liczbę zespoloną **complex** i zwraca również liczbę zespoloną. | ||
+ | |||
+ | ===== Inne funkcje ===== | ||
+ | |||
+ | Podobnie jak funkcje trygonometryczne funkcje ''exp()'', ''log()'', ''log10()'' i ''sqrt()'' zostały rozszerzone dla liczb zespolonych. Jako argument biorą obiekt ''**complex**'' i zwracają również obiekt ''**complex**''. | ||
+ | |||
+ | Biblioteka standardowa definiuje kilka wersji funkcji ''pow()''. Istnieją osobne definicje dotyczące podnoszenia liczb zespolonych do wartości całkowitej, zespolonej i rzeczywistej. Podobnie można podnosić wartość rzeczywistą do wartości ''**complex**''. | ||
+ | |||
+ | ===== Przykładowy program ===== | ||
+ | |||
+ | W poniższym kodzie zebrano przykłady dostępne na tej stronie opisujące podstawowe funkcje klasu ''**complex**''. Ponadto dodano prostą funkcję obrazującą przykładowe zastosowanie klasy w celu obliczenia pierwiastków funkcji kwadratowej o współczynnikach zespolonych. Poniższy kod dostępny jest {{complex:complex.cpp|tutaj}}. | ||
+ | |||
+ | <code cpp> | ||
+ | /* | ||
+ | Autor: Łukasz Romanowski | ||
+ | |||
+ | Biblioteka standarodowa: <complex> | ||
+ | |||
+ | Opis: Klasa szablonowa complex służy do reprezentacji i manipulacji liczbami zespolonymi. | ||
+ | Operacje zdefiniowane na liczbach zespolonych pozwalają na swobodne mieszanie obiektów tej | ||
+ | klasy z wbudowanymi typami numerycznymi. Należy zauważyć, że większość operacji wykonywanych | ||
+ | na obiektach tej klasy to zwykłe funkcje. Wyjątkami są metody real() i imag() należące do klasy complex. | ||
+ | */ | ||
+ | |||
+ | #include <iostream> | ||
+ | #include <complex> | ||
+ | #include <utility> | ||
+ | |||
+ | using namespace std; | ||
+ | |||
+ | typedef complex<double> Complex; | ||
+ | |||
+ | // deklaracja funkcji obliczajacej pierwiastki kwadratowe równania o współczynnikach zespolonych | ||
+ | // implementacja poniżej | ||
+ | pair<Complex, Complex> roots (Complex a, Complex b, Complex c); | ||
+ | |||
+ | int main() { | ||
+ | // deklaracje wykorzystujące rózne konstruktory dostępne w bibliotece standardowej | ||
+ | complex<double> cplx_one; // wartość 0 + 0i | ||
+ | complex<double> cplx_two(3.14); // wartość 3.14 + 0i | ||
+ | complex<double> cplx_three(1.5, 3.14); // wartość 1.5 + 3.14i | ||
+ | complex<double> cplx_four(cplx_two); // wartość również 3.14 + 0i | ||
+ | |||
+ | cout << "cplx_one: " << cplx_one << endl; | ||
+ | cout << "cplx_two: " << cplx_two << endl; | ||
+ | cout << "cplx_three: " << cplx_three << endl; | ||
+ | cout << "cplx_four: " << cplx_four << endl; | ||
+ | |||
+ | // wykorzystanie operatora przypisania oraz konwersji za pomocą konstruktora jednoargumentowego | ||
+ | cplx_one = cplx_three; // staje się 1.5 + 3.14i | ||
+ | cplx_three = 2.17; // staje się 2.17 + 0i | ||
+ | |||
+ | cout << "cplx_one: " << cplx_one << endl; | ||
+ | cout << "cplx_three: " << cplx_three << endl; | ||
+ | |||
+ | // wykorzystanie funkcji polar() do konstrukcji liczby zespolonej na podstawie modułu i kąta fazowego | ||
+ | cplx_four = polar(5.6, 1.8); | ||
+ | |||
+ | cout << "cplx_four: " << cplx_four << endl; | ||
+ | |||
+ | // wartosc sprzężoną otrzymujemy za pomocą funkcji conj() | ||
+ | complex<double> cplx_five = conj(cplx_four); | ||
+ | |||
+ | cout << "cplx_five: " << cplx_five << endl; | ||
+ | |||
+ | // aby otrzymać wartości części rzeczywistej i urojonej korzystamy z funkcji real() i imag() | ||
+ | cout << cplx_one.real() << "+" << cplx_one.imag() << "i" << endl; | ||
+ | cout << real(cplx_one) << "+" << imag(cplx_one) << "i" << endl; | ||
+ | |||
+ | // operatory można wykorzystywać zgodnie z przyjętą konwencją | ||
+ | cout << cplx_one + cplx_two << endl; // wartość (4.64,3.14) | ||
+ | cout << cplx_one - 3.14 << endl; // wartość (-1.64,3.14) | ||
+ | cout << 2.75 * cplx_two << endl; // wartość (8.635,0) | ||
+ | cout << (cplx_one += cplx_three / 2.0) << endl; // wartość (2.585,3.14) | ||
+ | |||
+ | // dostepne są również operatory jednoargumentowe + i - | ||
+ | cout << -cplx_one << endl; // wartość (-2.585,-3.14) | ||
+ | |||
+ | // do porównania wartości dwóch liczb zespolonych używamy operatorów == i !=, | ||
+ | // pozostałe operatory porównujące są niedostępne | ||
+ | cout << (cplx_one == cplx_three) << endl; // wartość 0 (fałsz) | ||
+ | cout << (cplx_one != cplx_three) << endl; // wartość 1 (prawda) | ||
+ | |||
+ | // wartości normalna i moduł dostępne są za pomocą funkcji norm() i abs() | ||
+ | cout << norm(cplx_two) << endl; | ||
+ | cout << abs(cplx_two) << endl; | ||
+ | |||
+ | // kąt fazowy można uzyskać za pomocą funkcji funkcji arg() | ||
+ | cout << cplx_four << " w postaci biegunowej wynosi " | ||
+ | << abs(cplx_four) << "e^" << arg(cplx_four) << "i"<< endl; | ||
+ | |||
+ | /* | ||
+ | przykład wykorzystania klasy complex<> do obliczenia pierwiastków równania danego wzorem: | ||
+ | (2,1)*x^2 + (0,1)*x + (5,0) = 0; | ||
+ | W celu przetestowania działania funkcji należy zmieniać wartości a, b i c dane poniżej | ||
+ | */ | ||
+ | |||
+ | Complex a(2,1); | ||
+ | Complex b(0,1); | ||
+ | Complex c(5,0); | ||
+ | |||
+ | pair<Complex,Complex> res(roots(a,b,c)); | ||
+ | |||
+ | cout << "Wyniki przykładowej funkcji roots() obliczającej pierwiastki równania" << endl | ||
+ | << a << "*x^2 + " << b << "*x + " << c << " = 0" << endl; | ||
+ | cout << " x1= " << res.first << endl; | ||
+ | cout << " x2= " << res.second << endl; | ||
+ | |||
+ | } | ||
+ | |||
+ | // definicja funkcji obliczajacej pierwiastki kwadratowe równania o współczynnikach zespolonych | ||
+ | pair<Complex, Complex> roots (Complex a, Complex b, Complex c) | ||
+ | { | ||
+ | Complex root = sqrt(b * b - 4.0 * a * c); | ||
+ | a *= 2.0; | ||
+ | return make_pair( | ||
+ | (-b + root)/a, | ||
+ | (-b - root)/a | ||
+ | ); | ||
+ | } | ||
+ | </code> | ||
+ | |||
+ | \\ | ||
+ | ---- | ||
+ | [[start]] >> [[biblioteka_standardowa]] |