ďťż

Ładny brzuch

Witam. Dostałem zadanie domowe, polegające na napisaniu ciał metod danej klasy, przy czym deklaracje w pliku nagłówkowym mam już podane. Nie rozumiem paru rzeczy i mam nadzieję, że ktoś łaskawy podpowie ;) Ogólnie program ma wykonywać działania na ułamkach zwykłych...

Oto klasa:
class CUlamek { private: int l, m; public: CUlamek(); CUlamek(int L, int M); CUlamek(const CUlamek &X); void Ustaw(); void Ustaw(const CUlamek &X); void Wyswietl(); void Ustaw(int L, int M); void Skroc(); float Dziesietny(); CUlamek Dodaj(const CUlamek &X); };

Teraz tak, CUlamek(); to konstruktor domyślny, czyli np:
CUlamek::CUlamek() { l=0; m=1; } Wywołuję go przy tworzeniu każdego obiektu tak? Tzn CUlamek A;??

Teraz nie rozumiem po co ma być ten drugi konstruktor CUlamek(int L, int M);?? Nie wystarczyłaby funkcja/metoda, która przypisuje wartości wprowadzone przez użytkownika?
Konstruktor kopiujący, z tego co wyczytałem powinien być, ale używa go kompilator tylko tak? Ja go nie wywołuje?

Dalej, po jakiego grzyba, 3 funkcje ustaw dotyczące wprowadzania danych??? No i CUlamek Dodaj(const CUlamek &X); WTF?? ;)

Kurcze, te klasy niby rozumiem, ale po co tyle tego wszystkigo?? Proszę o jakieś niesłownikowe, ale bardziej na "chłopski rozum", wytłumaczenie ;) Pozdrawiam...



1. Konstruktor domyślny jest potrzebny na przykład po to, abyś mógł przechowywać obiekty tej klasy w tablicy. No bo gdyby go nie było, to wtedy taki kod:
CUlamek ulamki[4];
nie zadziała, bo kompilator ma tylko do dyspozycji konstruktor CUlamek(int L, int M) i nie wie, co wpisać.

2. Ten drugi konstruktor CUlamek(int L, int M) jest po to, abyś mógł podać przy tworzeniu obiektu wartości licznika i mianownika. Masz rację, nie jest niezbędny, możesz zrobić:
CUlamek ulamek; ulamek.Ustaw(1, 2);
Ale to nieekonomicznie, ponieważ wykonujesz 2 podstawienia na zmienne l i m. W tym przypadku to nie ma znaczenia, ale w przypadkach, gdy operujesz na większych obiektach niż int'y (np obrazki BMP) to już robi różnicę.

3. Konstruktor kopiujący w tym przypadku jest niepotrzebny, bo kompilator potrafi wygenerować prawidłowy. No ale są przypadki, gdy bez niego ani rusz ;) Tak, kompilator go wywołuje. Ty też możesz.
4. Trzy metody Ustaw... Ta bezparametrowa to nie wiem po co... Te pozostałe to chyba jasne? W jednej podajesz licznik i mianownik ułamka, a w drugiej ułamek do skopiowania. Tak naprawdę to jest powielenie konstruktora kopiującego...
5. CUlamek Dodaj(const CUlamek &X); - moja interpretacja jest taka: ta metoda dodaje podany jako argument ułamek i zwraca wynik.
6. Twoja propozycja konstruktora bezargumentowego jest dobra, ale lepsza jest taka:
CUlamek::CUlamek() : l(0), m(1) { }

Mam nadzieję, że pomogłem :)

PS to nieistotne, ale "tradycja" mówi, że nazwy funkcji zaczyna się małą literą, zaś nazwy pól w klasie kończy się znakiem "_" - np int l_; :)
Ta propozycja pliku nagłówkowego jest niedoskonała. Dał Ci ją twój nauczyciel/wykładowca?
Użytkownik eugeniusz edytował ten post 18 marzec 2010, 00:27

1. Konstruktor domyślny jest potrzebny na przykład po to, abyś mógł przechowywać obiekty tej klasy w tablicy. No bo gdyby go nie było, to wtedy taki kod:
CUlamek ulamki[4];
nie zadziała, bo kompilator ma tylko do dyspozycji konstruktor CUlamek(int L, int M) i nie wie, co wpisać.

2. Ten drugi konstruktor CUlamek(int L, int M) jest po to, abyś mógł podać przy tworzeniu obiektu wartości licznika i mianownika. Masz rację, nie jest niezbędny, możesz zrobić:
CUlamek ulamek; ulamek.Ustaw(1, 2);
Ale to nieekonomicznie, ponieważ wykonujesz 2 podstawienia na zmienne l i m. W tym przypadku to nie ma znaczenia, ale w przypadkach, gdy operujesz na większych obiektach niż int'y (np obrazki BMP) to już robi różnicę.

3. Konstruktor kopiujący w tym przypadku jest niepotrzebny, bo kompilator potrafi wygenerować prawidłowy. No ale są przypadki, gdy bez niego ani rusz ;) Tak, kompilator go wywołuje. Ty też możesz.
4. Trzy metody Ustaw... Ta bezparametrowa to nie wiem po co... Te pozostałe to chyba jasne? W jednej podajesz licznik i mianownik ułamka, a w drugiej ułamek do skopiowania. Tak naprawdę to jest powielenie konstruktora kopiującego...
5. CUlamek Dodaj(const CUlamek &X); - moja interpretacja jest taka: ta metoda dodaje podany jako argument ułamek i zwraca wynik.
6. Twoja propozycja konstruktora bezargumentowego jest dobra, ale lepsza jest taka:
CUlamek::CUlamek() : l(0), m(1) { }

Mam nadzieję, że pomogłem :)

PS to nieistotne, ale "tradycja" mówi, że nazwy funkcji zaczyna się małą literą, zaś nazwy pól w klasie kończy się znakiem "_" - np int l_; :)
Ta propozycja pliku nagłówkowego jest niedoskonała. Dał Ci ją twój nauczyciel/wykładowca?


Pomogłeś i to bardzo ;) ... Jeszcze tylko w ramach uściślenia. Konstruktora drugiego oraz kopiującego właściwie w moim programie nie muszę używać?! Stworzę obiekt, konstruktor domyślny przypisze licznikowi i mianownikowi wartości, a później wartości te "nadpisze" użytkownik? :)

Plik nagłówkowy można powiedzieć, że dał wykładowca, ale w zasadzie to robiliśmy go wspólnie, na zajęciach, więc mogły wkraść się niedoskonałości ;)


Pomogłeś i to bardzo ;) ... Jeszcze tylko w ramach uściślenia. Konstruktora drugiego oraz kopiującego właściwie w moim programie nie muszę używać?! Stworzę obiekt, konstruktor domyślny przypisze licznikowi i mianownikowi wartości, a później wartości te "nadpisze" użytkownik? :)

Plik nagłówkowy można powiedzieć, że dał wykładowca, ale w zasadzie to robiliśmy go wspólnie, na zajęciach, więc mogły wkraść się niedoskonałości ;)

Nie. Konstruktora kopiującego nie musisz pisać, kompilator go stworzy sam. Ale nie używać go się nie da. Używasz go choćby przy podstawianiu.
Konstruktor z parametrami l i m jest najbardziej wskazany i on powinien być przede wszystkim.
Co do niedoskonałości, proponowałbym napisać tak:
void Wyswietl() const; float Dziesietny() const;
Ponieważ te metody nie zmieniają stanu obiektu.




Nie. Konstruktora kopiującego nie musisz pisać, kompilator go stworzy sam. Ale nie używać go się nie da. Używasz go choćby przy podstawianiu.
Konstruktor z parametrami l i m jest najbardziej wskazany i on powinien być przede wszystkim.
Co do niedoskonałości, proponowałbym napisać tak:
void Wyswietl() const; float Dziesietny() const;
Ponieważ te metody nie zmieniają stanu obiektu.


Konstruktor kopiujący przy podstawianiu, tzn?

Co do konstruktora z parametrami, to cały czas mam wątpliwość, po co miałbym tworzyć obiekt od razu z konkretnymi wartościami, skoro ma wprowadzić je użytkownik?! Mógłbyś podać jakiś konkretny przykład (dot. mojego programu) gdzie mógłbym go użyć? Przepraszam, zapewne to banalne, ale naprawdę się już gubię :P


Konstruktor kopiujący przy podstawianiu, tzn?

Co do konstruktora z parametrami, to cały czas mam wątpliwość, po co miałbym tworzyć obiekt od razu z konkretnymi wartościami, skoro ma wprowadzić je użytkownik?! Mógłbyś podać jakiś konkretny przykład (dot. mojego programu) gdzie mógłbym go użyć? Przepraszam, zapewne to banalne, ale naprawdę się już gubię :P


Nie masz powodu do przepraszania, nikt nie urodził się z tą wiedzą ;)

Konstruktor kopiujący wywołuje się w takich przypadkach:
CUlamek ulamek1(1, 2); CUlamek ulamek2; ulamek2 = ulamek1; // konstruktor kopiujący CUlamek ulamek3(ulamek1); // znów konstruktor kopiujący

Na powyższym przykładzie masz też przykład użycia konstruktora z parametrami.
Zamiast
CUlamek u; u.Ustaw(1, 2);
Wystarczyło napisać CUlamek u(1, 2);
Prościej i szybciej :)

Jeszcze jeden przykład. Z interakcją użytkownika :)
using std::cout; using std::cin; int main() { int licznik, mianownik; cout << "Podaj licznik: "; cin >> licznik; cout << "\nPodaj mianownik: "; cin >> mianownik; CUlamek mojUlamek(licznik, mianownik); // konstruktor z parametrami }


Nie masz powodu do przepraszania, nikt nie urodził się z tą wiedzą ;)

Konstruktor kopiujący wywołuje się w takich przypadkach:
CUlamek ulamek1(1, 2); CUlamek ulamek2; ulamek2 = ulamek1; // konstruktor kopiujący CUlamek ulamek3(ulamek1); // znów konstruktor kopiujący

Na powyższym przykładzie masz też przykład użycia konstruktora z parametrami.
Zamiast
CUlamek u; u.Ustaw(1, 2);
Wystarczyło napisać CUlamek u(1, 2);
Prościej i szybciej :)

Jeszcze jeden przykład. Z interakcją użytkownika :)
using std::cout; using std::cin; int main() { int licznik, mianownik; cout << "Podaj licznik: "; cin >> licznik; cout << "\nPodaj mianownik: "; cin >> mianownik; CUlamek mojUlamek(licznik, mianownik); // konstruktor z parametrami }


Dziękuję pięknie ;) Dużo mi się rozjaśniło. Teraz tylko ćwiczyć ;)

Pozdrawiam.

  • zanotowane.pl
  • doc.pisz.pl
  • pdf.pisz.pl
  • zsf.htw.pl
  •