To jest stara wersja strony!
Algorytm power podnosi obiekt klasy dowolnej klasy (o ile spełnia pewne wymagania) do zadanego wykładnika będącego nieujemną liczbą całkowitą. Algorytm korzysta z operatora * dlatego też, aby używać funkcji szablonowej power na własnych klasach należy przeładować operator * oraz =.
Algorytm jest zdefiniowany w pliku nagłówkowym numeric lub też, niestandardowym, wstecznie kompatybilnym, algo.h.
#include <numeric>
Power jest przeładowaną nazwą. Istnieją dwie wersje algorytmu power
template <class T, class Integer> inline T power(T x, Integer n); template <class T, class Integer, class MonoidOperation> T power(T x, Integer n, MonoidOperation op);
Oraz występujący w drugiej wersji power:
Obie wersje algorytmu zwracają obiekt takiego samego typu jak pierwszy argument funkcji.
power(T x, Integer n) zwraca wartość x * x …. * x, gdzie x jest powtórzone n razy. Kiedy n = 0, wartość zwracana wynosi identity_element(multiplies<T>()).
Druga wersja (power(T x, Integer n, MonoidOperation op) )jest podobna do pierwszej. Różnica polega na tym iż zamiast operacji * ( multiplies<T> ) wykonywana jest operacja op. Kiedy n = 0 funkcja zwraca identity_element(op). Obie funkcje należy zdefiniować, tworząc np. funktor oraz przeładowując identity_element().
Ponieważ kolejne mnożenie przez siebie kolejnych wartości (n-1 razy) byłoby nieefektywne, power implementuje „algorytm chłopów rosyjskich”. Jego złożoność obliczeniowa wynosi log2(n) + n1(n) gdzie log2 jest logarytmem o podstawie 2 z liczby n, a n1(n) jest liczbą jedynek w zapisie binarnym liczb n. Nie zawsze power wykonuje minimalną liczbę mnożeń; np. możliwe jest podniesienie wartości do potęgi piętnastej wykonując tylko pięć operacji mnożenia; power() wykonuje sześć. Dla prostych elementów nie powoduje to znaczącej różnicy, ale dla np. wielowymiarowych macierzy własna metoda podnoszenia do potęgi mogłaby być efektywniejsza czasowo.
Algorytm power nie wymaga aby operacja mnożenia na obiektach typu T była przemienna, natomiast krytyczne jest aby operacja ta była łączna. Jeśli operacja * lub op na obiektach klasy T nie jest łączna wtedy power zwróci złą wartość.
na obiektach klas wbudowanych:
int main() { cout << "2 ** 30 = " << power(2, 30) << endl; }
na obiektach klas zdefiniowanych przez użytkownika:
void main(void) { //stworzenie macierzy o wymiarze 3x3 zawierajacej 2 na przekątnej macierz<3> pierwsza(2); //wstawienie 4 na miejscu (1,2) oraz (3,2) - pola są numerowane od 1 do wymiar pierwsza.wstaw(1,2,4); pierwsza.wstaw(3,2,4); //wyswietlenie przykladowo stworzonej macierzy cout << pierwsza << "\n"; //stworzenie macierzy jednostkowej i jej wyswietlenie na ekranie macierz<3> druga(1); cout << druga << "\n"; // stworzenie macierzy zerowej; dodanie pierwszej i drugiej oraz przypisanie sumy do trzeciej macierz<3> trzecia; trzecia = pierwsza + druga; cout << trzecia << "\n"; //wyswietlenie wyniku dla operacji power(x,0) //w przypadku macierzy wynikiem takiej operacji jest maciez jednostkowa //pierwszy rodzaj algorytmu power cout << power(trzecia,0) << "\n"; //drugi rodzaj algorytmu power cout << power(trzecia,0,mnozenie<3>()) << "\n"; //stworzenie macierzy zerowej i przypisanie do niej wyniku podnoszenia macierzy do potegi 3 macierz<3> czwarta; czwarta = power(trzecia,3,mnozenie<3>()); cout <<czwarta << "\n"; }