28 kwietnia 2015 JSLib 4.1 Dokumentacja Spis treści 1 Wprowadzenie 2 2 Klasa BigInt 2 2.1 Tworzenie liczb....................... 2 2.2 Operacje wejścia-wyjścia.................. 3 2.3 Operatory.......................... 3 2.4 Metody teorioliczbowe................... 4 2.5 Metody różne........................ 5 3 Klasa ByteTab 5 3.1 Tworzenie tablicy bajtów.................. 5 3.2 Operatory.......................... 6 3.3 Metody........................... 6 4 Klasa BMPImage 7 4.1 Tworzenie obrazu...................... 7 4.2 Metody........................... 7 4.3 Porównywanie pikseli.................... 9 5 Klasa CWave 9 5.1 Tworzenie ścieżki...................... 10 5.2 Metody........................... 10 6 Nagłówek EasyLife 11 7 Przykłady 12 7.1 HelloWorld - operacje wejścia-wyjścia.......... 12 7.2 Generowanie liczby pierwszej................ 13 7.3 Zapis i odczyt liczb z pliku................. 14 7.4 Progrowanie obrazka.................... 15 1
1 Wprowadzenie Biblioteka JSLib została zaprojektowana jako narzędzie do pracy na laboratoriach przetwarzania dźwięku i obrazu oraz laboratoriach z przedmiotów kryptograficznych. Głównym jej założeniem było zapewnienie maksymalnego ułatwienia pracy studentom na laboratoriach, jednocześnie przyjmując, że posiadają oni niewielką wiedzę z języka C++. Biblioteka ta nie wymaga instalacji. Należy jedynie do tworzonego kodu dołączyć pliki biblioteki. Aby ułatwić rozpoczęcie pracy z biblioteką została przygotowana startowa skonfigurowana solucja w Visual Studio 2010 zwierająca wszystkie niezbędne pliki biblioteki oraz przykładowy program. Biblioteka działa również w nowszych wersjach Visual Studio. Prezentowane w tej dokumentacji przykłady będą zgodne ze ścieżkami przyjętymi w tej solucji. Kod źródłowy biblioteki jest zgodny ze standardem C++ i jest w pełni przenośny. 2 Klasa BigInt Klasa BigInt definiuje liczbę całkowitą dowolnej wielkości. Klasa ta wyposażona jest w podstawowe algorytmy teorii liczb. Posiada również możliwość wykonywania operacji bezpośrednio na reprezentacji bitowej liczby. Każda liczba całkowita, ze względu na zmienną długość reprezentacji bitowej, posiada zapis w postaci znak - moduł. 2.1 Tworzenie liczb BigInt a; - utworzenie dużej liczby całkowitej równej 0. BigInt a( 123 ); - utworzenie dużej liczby całkowitej równej podanej wartości typu char lub int. Zakres wartości podanych w nawiasach to 2 31,... 2 31 1. BigInt a = 123; - jak wyżej. BigInt a( "-123" ); - utworzenie dużej liczby całkowitej na podstawie dowolnie długiego łańcucha znaków, który zawiera zapis liczby przy podstawie 10. BigInt a( string("-123") ); - jak wyżej, przy złożeniu, że łańcuch znaków jest obiektem typu string. 2
BigInt a( b ); - utworzenie dużej liczby całkowitej o wartości równej innej dużej liczbie całkowitej. 2.2 Operacje wejścia-wyjścia Operatory << oraz >> w kontekście strumieni wejściowych lub wyjściowych służą do pobierania i wypisywania dużej liczby całkowitej przy podstawie 10. BigInt a; cin >> a; cout << a; // wczytanie z klawiatury // wypisanie na konsolę 2.3 Operatory Operatory arytmetyczne - zaimplementowano dodawanie +, odejmowanie -, mnożenie dwóch dużych liczb * oraz dzielenie całkowitoliczbowe /. Dostępna jest również reszta z dzielenia %. Dla każdego z operatorów dostępne są skrótowe zapisy: += -= *= /= %=. Operatory inkrementacji - zaimplementowano operator ++ w wersji przedrostkowej i przyrostkowej. Operatory relacyjne - zaimplementowano operatory relacyjne: ==!= < > <= >= Operatory bitowe - zaimplementowano przesunięcie binarnej reprezentacji dużej liczby całkowitej w prawo o podaną ilość pozycji >> oraz w lewo o podaną ilość pozycji <<. Dla każdego z operatorów dostępne są skrótowe zapisy: <<= >>=. BigInt a(1), b(4); a <<= 1; b >>= 1; if( a == b ) // warunek będzie prawdziwy //... 3
Operator indeksowania - oznaczony symbolem [] - zwraca cyfrę dziesiętną o podanym indeksie. Indeksowanie rozpoczyna się od zera. Operator przypisania - operator = służy do wartości z innej dużej liczby całkowitej, liczb typów int, char oraz stałych łańcuchów znaków. BigInt a, b; a = 12; b = a; b = z ; b = "123456789123456789"; 2.4 Metody teorioliczbowe bool ispositive() - zwraca true gdy liczba jest dodatnia bool isodd() - zwraca true gdy liczba jest nieparzysta bool isprime() - zwraca true gdy liczba jest pierwsza BigInt nextprime() - zwraca następną liczbę pierwszą większą od danej liczby BigInt a(19), b; b = a.nextprime(); cout << b; // wypisze 23 BigInt godddivisor() - zwraca największy nieparzysty dzielnik r, gdzie liczba = (2 s ) r BigInt godddivisor( x ) - jak wyżej, przy czym do zmiennej x w argumencie wstawia obliczone s BigInt sqrt() - zwraca część całkowitą pierwiastka z liczby, lub zero gdy jest ona ujemna. BigInt square() -zwraca kwadrat liczby BigInt powermod( e, m ) - zwraca wartość (liczba) e mod m 4
BigInt inversemod( m ) - oblicza odwrotność liczby modulo m. Gdy liczba nie jest odwracalna zwraca 0. BigInt gcd( b ) - oblicza największy wspólny dzielnik liczby oraz argumentu b BigInt lcm( b ) - oblicza najmniejszą wspólną wielokrotność liczby oraz argumentu b 2.5 Metody różne BigInt& random( n ) - wygeneruje losową liczbę nieujemną n-bitową (z zakresu 0,..., 2 n 1). Argument n można pominąć wtedy zostanie założone n=32. int toint() - zwraca liczbę typu int utworzoną z pierwszych 30 bitów dużej liczby całkowitej. Znak liczby jest zachowany. std::string tostring( base ) - zwraca łańcuch znaków z zapisem liczby przy podstawie base (zakres podstaw 2,..., 16). Argument base można pominąć wtedy zostanie założone base=10. unsigned int size() - zwraca ilość cyfr w zapisie dziesiętnym unsigned int bitsize() - zwraca ilość bitów unsigned int bitat( idx ) zwraca bit o podanym indeksie idx. Indeksowanie rozpoczyna się od jeden. void fromhex( s ) - tworzy wartość dużej liczby całkowitej na podstawie podanego łańcucha znaków s zawierającego zapis liczby przy podstawie 16. 3 Klasa ByteTab Klasa ByteTab definiuje obiekty służące do przechowywania bajtów ze swobodnym dostępem do nich poprzez indeksowanie. Jednocześnie zakłada się łatwy sposób wczytania i zapisania zawartości tych obiektów do pliku. 3.1 Tworzenie tablicy bajtów ByteTab t; - utworzenie pustej tablicy bajtów 5
ByteTab t( b ); - utworzenie tablicy bajtów na podstawie innej tablicy bajtów b ByteTab t( "plik.txt" ); - utworzenie tablicy bajtów zawierającej wszystkie bajty podanego pliku (niekoniecznie tekstowego) ByteTab t( n, v ); - utworzenie tablicy n bajtów wypełnionych wartością v. Argument v można pominąć wtedy zostanie założone v=0. 3.2 Operatory Operatory sklejania - użycie operatora + na dwóch tablicach bajtów spowoduje utworzenie nowej tablicy będącej ich sklejeniem. Operator += dołącza do istniejącej tablicy bajtów bajty ze wskazanej tablicy. Operatory przypisania - operator = służy do kopiowania zawartości tablic bajtów. Dopuszcza się, aby prawym argumentem był łańcuch znaków, wtedy jest on konwertowany na tablicę. Operator indeksowania - oznaczony symbolem [] - zwraca referencję do bajtu o podanym indeksie. W przypadku użycia nieistniejącego indeksu zostaną utworzone bajty zerowe aż do tego indeksu włącznie. 3.3 Metody bool fromfile( filename ) - tworzy zawartość tablicy na podstawie bajtów z pliku bool tofile( filename ) - tworzy plik o bajtach takich jak zawarte w tablicy void push_back( z ) - dodaje nowy bajt z (jest on typu unsigned char) do tablicy, na jej końcu void pop_back() - usuwa ostatni element tablicy int size() - zwraca rozmiar tablicy bajtów void clear() - czyści tablicę std::string tostring( start_index, stop_index ) - zwraca przekonwertowaną tablicę bajtów na łańcuch znaków począwszy od bajta o indeksie start index aż do bajta o indeksie stop index, albo aż do wartości zero jeśli taka wystąpi wcześniej. Jeżeli argument stop index 6
zostanie pominięty wtedy konwersja odbywa się do końca tablicy. Jeżeli oba argumenty zostaną pominięte, wtedy cała tablica jest konwertowana. std::string sha256() - zwraca łańcuch znaków zawierający zapis przy podstawie 16 wartości funkcji skrótu SHA-256 obliczonej dla tej tablicy // Wczytanie skrótu pliku do BigInt ByteTab t( "plik.txt" ); BigInt a; a.fromhex( t.sha256() ); 4 Klasa BMPImage Klasa BMPImage definiuje obraz rastorowy o 24 bitowej głębi kolorów. Każdy piksel obrazu jest reprezentowany przez składowe red, green, blue. 4.1 Tworzenie obrazu BMPImage obraz - tworzy jednopikselowy obraz BMPImage obraz( x, y ) - tworzy obraz o wymiarach x na y BMPImage obraz( "plik.bmp" ) - tworzy obraz na podstawie pliku w formacie BMP. Klasa ta obsługuje jedynie nieskompresowane pliki o 24 bitowej głębi kolorów. 4.2 Metody int width() int height() Pixel& pixel( x, y ) - zapewnia dostęp do piksela o podanych współrzędnych x i y. 7
// Manipulowanie kolorem piksela BMPImage obraz( "plik.bmp" ); obraz.pixel( 10, 10 ).red = 255; obraz.pixel( 1, 2 ) = Pixel( 0, 255, 0 ); void togray() - zamienia obraz na zapisany w skali szarości. Wszystkie składowe koloru red, green, blue występują i mają tę samą wartość. void negative() - wykonuje negatyw void tofile( "out.bmp" ) - zapisuje obraz do pliku o podanej nazwie w formacie BMP. void tofile( "dwa.bmp", innyobraz ) - tworzy plik o podanej nazwie w formacie BMP zawierający dwa obrazy (obiektu na którym jest wywołana metoda oraz obiektu przekazanego w argumencie) void drawline( x1, y1, x2, y2, r, g, b ) - rysuje linię od współrzędnych (x1,y1) do współrzędnych (x2,y2) w kolorze o składowych r, g, b. void drawrect( x1, y1, x2, y2, r, g, b ) - rysuje prostokąt rozpięty na wierzchołkach o współrzędnych (x1,y1) i (x2,y2) w kolorze o składowych r, g, b. void drawfilledrect( x1, y1, x2, y2, r, g, b ) - rysuje wypełniony prostokąt rozpięty na wierzchołkach o współrzędnych (x1,y1) i (x2,y2) w kolorze o składowych r, g, b. void convolution( t ) - konwolucja obrazu na podstawie 9 elementowej tablicy t liczb typu double. // Wyostrzenie obrazu BMPImage obraz( "plik.bmp" ); double t[]={ 0,-1,0,-1,5,-1,0,-1,0 }; obraz.convolution( t ); obraz.tofile( "out.bmp" ); 8
void fill( x, y, r, g, b ) - wypełnia obszar zawierający punkt o współrzędnych (x,y) kolorem o składowych r, g, b. void show( zoom ) - otwiera okno zawierające obraz (albo powiększony obraz). Argument zoom można pominąć wtedy zostanie założone zoom=1. Dopuszczalne wartości parametru zoom to liczby całkowite od 1 do 16. void showwith( innyobraz ) - otwiera okno zawierające dwa obrazy (obiektu na którym jest wywołana metoda oraz obiektu przekazanego w argumencie) BMPImage obraz1( "plik.bmp" ); BMPImage obraz2( obraz1 ); double t[]={ 0,-1,0,-1,5,-1,0,-1,0 }; obraz2.convolution( t ); obraz1.showwith( obraz2 ); 4.3 Porównywanie pikseli Istnieje możliwość porównywania pikseli: BMPImage obraz( "plik.bmp" ); if( obraz.pixel( 10, 10 ) == Pixel( 0, 0, 0 ) ) obraz.pixel( 10, 10 ) = Pixel( 255, 255, 255 ); if( obraz.pixel( 20, 20 )!= Pixel( 0, 0, 0 ) ) obraz.pixel( 20, 20 ) = Pixel( 0, 0, 0 ); 5 Klasa CWave Klasa CWave definiuje stereofoniczną ścieżkę dźwiękową. W klasie tej można przechowywać nieskompresowany dźwięk w rozdzielczości 16 bitowej o częstotliwości próbkowania 44100 Hz. 9
5.1 Tworzenie ścieżki CWave() - tworzy pustą ścieżkę (bez próbek) CWave( n ) - tworzy ścieżkę z ciszą o n próbkach CWave( "plik.wav" ) - tworzy ścieżkę na podstawie pliku w formacie WAVE. Klasa to obsługuje dźwięk stereofoniczny w rozdzielczości 16 bitowej o częstotliwości próbkowania 44100 Hz. 5.2 Metody unsigned int size() - zwraca ilość próbek bool tofile( "out.wav" ) - zapisuje ścieżkę dźwiękową do pliku Sample& operator[]( n ) - zapewnia dostęp do stereofonicznej próbki o podanym indeksie. Kanały w próbce występują pod nazwami left i right. Dopuszczalne wartości jakie można zapisać w jednym kanale są z zakresu: -32768,..., 32767. CWave dzwiek( "plik.wav" ); dzwiek[ 5 ].left = 10000; dzwiek[ 10 ] = Sample( 0, 0 ); void mixwith( innycwave ) - miksuje ścieżkę z innym obiektem tej klasy void scale( x ) - skaluje próbki. Argument x jest typu double. Jego wartość 1.0 oznacza identyczność. void play() - odtwarza ścieżkę audio na domyślnej karcie dźwiękowej 10
6 Nagłówek EasyLife Dołączenie nagłówka EasyLife.h do programu ułatwia pracę osobie implementującej algorytmy. Zostaną automatycznie dołączone wszystkie niezbędne nagłówki oraz zostanie włączona standardowa przestrzeń nazw. Generator liczb pseudolosowych zostanie zainicjowany czasem systemowym. Przed zakończeniem programu okno konsoli nie zniknie dopóki użytkownik nie naciśnie dowolnego klawisza. #include "JSLib/EasyLife.h" int main() { // własny kod } return 0; 11
7 Przykłady 7.1 HelloWorld - operacje wejścia-wyjścia #include "JSLib/EasyLife.h" int main() { BigInt a, b,c; cin >> a; cin >> b; c = a * b; cout << c << endl; } return 0; 12
7.2 Generowanie liczby pierwszej Wygenerowanie co najmniej 100-bitowej losowej liczby pierwszej: #include "JSLib/EasyLife.h" int main() { BigInt a(1), b; a <<= 99; b.random( 64 ); a += b; b = a.nextprime(); cout << b << endl; cout << b.bitsize() << endl; } return 0; 13
7.3 Zapis i odczyt liczb z pliku #include "JSLib/EasyLife.h" int main() { // Zapis BigInt a( "123" ); ByteTab t; t = a.tostring(); t.tofile( "liczba.txt" ); // Odczyt ByteTab s( "liczba.txt" ); BigInt b( s.tostring() ); cout << b << endl; } return 0; 14
7.4 Progrowanie obrazka #include "JSLib/EasyLife.h" int main() { BMPImage im( "plik.bmp" ); int value = 0; cout << " Podaj prog: "; cin >> value; for( int y=0; y<im.height(); y++ ) for( int x=0; x<im.width(); x++ ) if( im.pixel( x, y ).red + im.pixel( x, y ).green + im.pixel( x, y ).blue < value ) im.pixel( x, y ) = Pixel( 0, 0, 0 ); else im.pixel( x, y ) = Pixel( 255, 255, 255 ); im.show(); im.tofile( "out.bmp" ); } return 0; 15