Ten artykuł rozpoczyna serię artykułów dotyczących implementacji ułamków. Konkretniej chodzi o stworzenie biblioteki, którą będzie można zaimplementować w dowolnym projekcie, aby można było swobodnie pracować na ułamkach (używając nowego typu danych). Przed przystąpieniem do pisania warto przypomnieć sobie definicję ułamka:
Ułamek to wyrażenie, gdzie a i b to dowolne wyrażenia algebraiczne.
Biblioteka będzie zawierać nową klasę ulamek. Pozwoli to na zadeklarowanie zmiennej tego typu w dowolnym miejscu w kodzie. Utworzenie nowej klasy rozpoczyna słowo kluczowe class i nazwa klasy
Następnie rozpoczyna się sekcja prywatna klasy. Jest to część hermetyzacji klasy. Ma to za zadanie ograniczyć co może wywołać programista na tej klasie. Pozostawienie niektórych z tych funkcji publicznych mogłoby doprowadzić do nieoczekiwanego przerwania działania programu (poprzez nieprawidłową operację). W prywatnej części są zadeklarowane dwie zmienne typu int, które odpowiadają licznikowi i mianownikowi ułamka.
Następnie do programu zostają wprowadzone prywatne funkcje pomocnicze. Ich zadanie polega na wykonaniu określonych operacji arytmetycznych. Przykładowo pierwsza funkcja dodaj() dodaje nowy ułamek do aktualnie przechowywanego w zmiennej.
Na podobnej zasadzie działają funkcje odejmij(), mnozenie() oraz dzielenie().
Ostatnią prywatną funkcją jest nwd(), która jest implementacją szukania największego wspólnego dzielnika przy pomocy Algorytmu Euklidesa. Funkcja ta zostanie użyta podczas redukowania ułamka.
Teraz w klasie zadeklarowana część publiczna. Świadczy o tym słowo kluczowe public. Część ta udostępni określone funkcje dla programisty. Pierwsza z nich to będzie konstruktor, który pozwoli utworzyć zmienną typu ulamek.
(2.) Konstruktor przyjmuje dwa argumenty _licznik oraz _mianownik. Argument _mianownik domyślnie ma wartość 1. Pozwoli to na utworzenie ułamka przy pomocy tylko wartości licznika. Są to wartości, które (3., 4.) zostaną przypisane do wcześniej zadeklarowanych zmiennych. Po przypisaniu program (5.) zredukuje ułamek.
Dodatkowo, aby można było tworzyć ułamek podając jedynie licznik zdefiniowany został konstruktor jednoargumentowy.
Użyta funkcja redukuj() wygląda następująco:
(1.) Funkcja nic nie zwraca. (2.) Oblicza największy wspólny dzielnik, a potem (3., 4.) dzieli zarówno licznik i mianownik przez wyliczoną wartość.
Pomimo zwiększenia precyzji przechowywania danych programista lub użytkownik mogą chcieć, aby program wypisał wartość dziesiętną przechowywanego ułamka. W tym celu można posłużyć się funkcją pobierzWartosc(), która podzieli licznik przez mianownik i zwróci liczbę rzeczywistą.
O ile do tej pory ciężko było znaleźć przewagę nowej klasy nad typowym przechowywaniem ułamka w zmiennej typu rzeczywistego to funkcja odwroc() z pewnością to zmieni. Potrafi ona odwrócić ułamek nie tracąc żadnych danych przez błąd przybliżenia.
Klasa ulamek jest już prawie gotowa, ale wciąż brakuje możliwości wykonywania operacji na ułamkach. Są oczywiście zadeklarowane, ale programista nie ma do nich dostępu. W celu uproszczenia wykonywanych operacji zadeklarowane zostaną operatory. Pozwoli to wykonywać operacje arytmetyczne na ułamku tak samo jak w przypadku prostych typów danych.
Pierwszy operator << ma za zadanie ułatwić wypisywanie ułamka na dowolny strumień danych. Ułamek zostanie wypisany w postaci licznik/mianownik.
Dalej zostaje zdefiniowany operacje dodawania:
Analogicznie do zadeklarowanych operatorów dodawania zostają zadeklarowane pozostałe operatory do wykonywania operacji arytmetycznych:
Pozostało teraz jeszcze dodać przykładowo konwersję liczb całkowitych na ułamki. Jest to niezwykle przydatna konwersja, która umożliwia mieszanie liczb całkowitych i ułamków nie definiując dodatkowych operatorów.
Na sam koniec deklaracji klasy nie należy zapomnieć o poprawnym zakończeniu klasy:
(1.) Tworzy ułamek. (2.) Podobnie jak w pierwszym przypadku . (3.) Utworzenie ułamka niewłaściwego
Operacje arytmetyczne można wykonać używając operatorów dwuargumentowych:
Można też oczywiście użyć operatorów skróconych co znacznie ułatwia zapis:
Po wykonaniu wszystkich operacji wyżej można wypisać dane w następujący sposób:
(1.) Wypisanie ułamka w postaci licznik/mianownik. (2.) Wypisanie wartości dziesiętnej ułamka oraz (3.) obcięcie części dziesiętnej wypisywanego ułamka.