Wykład 4:
Klasa
Podstawa języka.
Każde pojęcie które chcemy opisać w języku musi
być zawarte w definicji klasy.
Klasa definiuje nowy typ danych, których
wartościami są obiekty:
●
klasa to szablon dla obiektów
●obiekt to egzemplarz klasy
Definicja Klasy
class nazwa { //deklaracje pól typ pole1; ... typ poleN; //deklaracje metod typ metoda1(lista-parametrów) { //treść metody } ... typ metodaM(lista-parametrów) { //treść metody } }Przykład Klasy
Klasa, która zawiera tylko trzy pola danych:
class Pudelko {
double szerokosc; double wysokosc; double glebokosc; }
Utworzenie obiektu klasy, i przypisanie wartości polu
tego obiektu:
Pudelko mojePudelko = new Pudelko(); mojePudelko.szerokosc = 100;
Wykorzystanie Klasy
class PudelkoDemo {
public static void main(String args[]) { Pudelko mojePudelko = new Pudelko();
double objetosc; mojePudelko.szerokosc = 10; mojePudelko.wysokosc = 20; mojePudelko.glebokosc = 15; objetosc = mojePudelko.szerokosc * mojePudelko.wysokosc * mojePudelko.glebokosc; System.out.println(“Objetosc to “, objetosc); } }
Kompilacja i Wykonanie
Należy umieścić obie klasy w pliku PudelkoDemo.java:
class Pudelko { ... } class PudelkoDemo {
public static void main(...) { ... } }
Kompilacja i wykonanie:
> cd demonstracje/PudelkoDemo > javac PudelkoDemo.java > java PudelkoDemoNiezależność Pól
Każdy obiekt ma własną kopie pól klasy: zmiana pola
jednego nie ma wpływu na wartości pól drugiego.
public static void main(String args[]) { Pudelko mojePudelko1 = new Pudelko(); Pudelko mojePudelko2 = new Pudelko(); double objetosc; mojePudelko1.szerokosc = 10; ... mojePudelko2.szerokosc = 3; ... objetosc = mojePudelko1.szerokosc * ...; System.out.println(“Objetosc: “ + objetosc); objetosc = mojePudelko2.szerokosc * ...; System.out.println(“Objetosc: “ + objetosc); }
Deklaracja Obiektów
Uzyskanie obiektów klasy, proces dwu-etapowy:
●
Deklaracja zmiennej typu klasy:
Box mybox;
Powstaje zmienna odwołująca się do obiektu, której
wartością jest na razie
null
.
●
Uzyskanie adresu obiektu i przypisanie go zmiennej.
Operator new
Alokuje pamięć dla obiektu i zwraca jego adres.
zmiennaKlasy = new nazwaKlasy();
●
nazwaKlasy():
konstruktor klasy
●
klasa może deklarować własny konstruktor, lub
korzystać z domyślnego
●
alokacja dynamiczna pamięci: tyle obiektów ile
potrzeba, ale pamięci może brakować
●
tworzenie zmiennych typów podstawowych nie
Przypisania Zmiennych Obiektowych
Przypisanie kopiuje adres, nie wartość:
Box b1 = new Box(); Box b2 = b1;
Obie zmienne wskazują na ten sam obiekt.
Zmiennie nie są w żaden sposób połączone:
...
b1 = null;
Metody Klasy
Ogólna postać definicji metody:
type nazwa(lista-parametrow) { //treść metody
return wartosc; //dalsza treść }
● type
jest typem wartości zwracanych
●
jeśli nie zwraca wartości, jej typem jest
void● nazwa jest nazwą metody
● lista-parametrow jest listą typów i nazw argumentów oddzielonych przecinkami
Metody Klasy: Przykład
Klasy definiują metody by ukrywać wewnętrzną
strukturę danych, jak też na własny użytek.
class Pudelko {
double szerokosc, wysokosc, glebokosc; //wyswietla objetosc pudelka
void objetosc() {
System.out.print(“Objetosc: “); System.out.println(
szerokosc * wysokosc * glebokosc); }
}
Odwołanie do pola w danej klasie można wykonać
bezpośrednio.
Metody Klasy: Przykład
public static void main(String args[]) { Pudelko mojePudelko1 = new Pudelko(); Pudelko mojePudelko2 = new Pudelko(); mojePudelko1.szerokosc = 10; ...
mojePudelko2.szerokosc = 3; ...
//wyswietl objetosc pierwszego pudelka mojePudelko1.objetosc();
//wyswietl objetosc drugiego pudelka mojePudelko2.objetosc();
}
Odwołanie do pola w innej klasie niż bieżąca musi odbyć
się przez obiekt tej klasy.
Metoda Która Zwraca Wartość
Typ wyrażenia które zwraca wartość metody musi być
zgodny z typem wyniku tej metody:
class Pudelko {
double szerokosc, wysokosc, glebokosc; //oblicza objetosc pudelka
double objetosc() {
return szerokosc * wysokosc * glebokosc;
} }
Metoda Która Zwraca Wartość
Typ zmiennej której przypisujemy wartość metody
musi być zgodny z typem wyniku tej metody:
public static void main(String args[]) { Pudelko mojePudelko1 = new Pudelko(); Pudelko mojePudelko2 = new Pudelko(); double objetosc; mojePudelko1.szerokosc = 10; ... mojePudelko2.szerokosc = 3; ... objetosc = mojePudelko1.objetosc(); System.out.println(“Objetosc: “ + objetosc); objetosc = mojePudelko2.objetosc(); System.out.println(“Objetosc: “ + objetosc); }
Metoda Która Posiada Parametry
Parametry zwiększają stosowalność metod.
●
Metoda bez parametrów:
int kwadrat() { return 10 * 10; }
●
Metoda z parametrem:
int kwadrat(int i) { return i * i; }
Parametr: zmienna która otrzymuje wartość gdy
metoda jest wykonywana.
Metoda z Parametrami: Przykład
class Pudelko {
double szerokosc, wysokosc, glebokosc; //oblicza objetosc pudelka
double objetosc() {
return szerokosc * wysokosc * glebokosc; }
//ustala wymiary pudelka
void ustalWymiary(double s, double w, double g) { szerokosc = s; wysokosc = w; glebokosc = g; } }
Metoda z Parametrami: Przykład
public static void main(String args[]) { Pudelko mojePudelko1 = new Pudelko(); Pudelko mojePudelko2 = new Pudelko(); double objetosc; mojePudelko1.ustalWymiary(10, 20, 15); mojePudelko2.ustalWymiary(3, 6, 9); objetosc = mojePudelko1.objetosc(); System.out.println(“Objetosc: “ + objetosc); objetosc = mojePudelko2.objetosc(); System.out.println(“Objetosc: “ + objetosc); }
Konstruktory
Konstruktor realizuje automatyczną inicjację obiektu
zaraz po jego utworzeniu.
Konstruktor posiada tą samą nazwę jak klasa w
której się znajduje.
Konstruktor piszemy bez typu wyniku: domyślnym
typem konstruktora klasy jest ta sama klasa.
Gdy klasa nie posiada konstruktora, domyślny
konstruktor automatycznie inicjuje pola zerami.
Konstruktor: Przykład
class Pudelko {
double szerokosc, wysokosc, glebokosc; //konstruktor pudelka Pudelko() { System.out.println(“Budujemy pudelko”); szerokosc = 10; wysokosc = 10; glebokosc = 10; }
//oblicza objetosc pudelka double objetosc() {
return szerokosc * wysokosc * glebokosc; }
Konstruktor: Przykład
public static void main(String args[]) {
Pudelko mojePudelko1 = new Pudelko(); Pudelko mojePudelko2 = new Pudelko();
double objetosc; objetosc = mojePudelko1.objetosc(); System.out.println(“Objetosc: “ + objetosc); objetosc = mojePudelko2.objetosc(); System.out.println(“Objetosc: “ + objetosc); }
Parametryzowany Konstruktor
Wszystkie pudełka mają tą samą objętość.
Potrzebujemy konstruktora, który tworzy pudełka
różnych rozmiarów.
class Pudelko {
double szerokosc, wysokosc, glebokosc; //parametryzowany konstruktor pudelka
Pudelko(double s, double w, double g) { szerokosc = s; wysokosc = w; glebokosc = g; } ... }
Parametryzowany Konstruktor
public static void main(String args[]) {
Pudelko mojePudelko1 = new Pudelko(10,20,15); Pudelko mojePudelko2 = new Pudelko(3,6,9);
double objetosc; objetosc = mojePudelko1.objetosc(); System.out.println(“Objetosc: “ + objetosc); objetosc = mojePudelko2.objetosc(); System.out.println(“Objetosc: “ + objetosc); }
Słowo Kluczowe this
Odwołanie z metody do obiektu który ją wywołał.
//zbedne uzycie “this”
Pudelko(double s, double w, double g) {
this.szerokosc = s; this.wysokosc = w; this.glebokosc = g;
}
Dozwolone wszędzie tam gdzie można odwołać się do
obiektu bieżącej klasy.
Przesłanianie Pól
Nielegalne jest deklarowanie dwóch zmiennych o tej
samej nazwie wewnątrz zawierających się bloków.
Legalne jest deklarowanie zmiennych lokalnych i
parametrów o tej samej nazwie jak pola klasy.
Następuje przesłonięcie pól przez zmienne lokalne.
Pudelko(double szerokosc, double wysokosc, double glebokosc) {
this.szerokosc = szerokosc; this.wysokosc = wysokosc; this.glebokosc = glebokosc; }
Metoda finalize()
Dodatkowe czynności do wykonania gdy obiekt jest
usuwany z pamięci, np. zwolnienie dostępu do pliku.
Wykonywane przez metodę finalize():
protected void finalize() { ...
}
Metoda wywoływana jest przez odśmiecacz pamięci
gdy ten usuwa niepotrzebny obiekt ze sterty.
Przykład: Klasa Stos
Stos przechowuje dane w porządku first-in last-out:
pierwszy zapisany, ostatni odczytany.
Oto implementacja 10-elementowego stosu:
class Stos {
int stos[] = new int[10]; int wskaznik; //inicjalizacja wskaznika Stos() { wskaznik = -1; }
Przykład: Klasa Stos
//zapis elementu na stosie void push(int element) { if (wskaznik == 9)
System.out.println(“Stos jest pelny.”); else
stos[++wskaznik] = element; }
//odczyt elementu ze stosu int pop() {
if (wskaznik < 0) {
System.out.println(“Stos jest pusty.”); return 0; } else return stos[wskaznik—]; } }
Przykład: Użycie Klasy Stos
class TestStos {
public static void main(String args[]) { Stos stos1 = new Stos();
Stos stos2 = new Stos();
for (int i=0; i<10; i++) stos1.push(i); for (int i=10; i<20; i++) stos2.push(i); System.out.println(“Pierwszy stos: “); for (int i=0; i<10; i++)
System.out.println(stos1.pop()); System.out.println(“Drugi stos: “); for (int i=0; i<10; i++)
System.out.println(stos2.pop()); }