1 Hernyák Zoltán Programozási Nyelvek II. Eszterházy Károly Főiskola Számítástudományi tsz
2 class Datum { public int napokSzama; // ota } class Datum { public int napokSzama; // ota } Datum d = new Datum(” ”); d = d+10; // 10 nappal léptetés előre d++; Datum d = new Datum(” ”); d = d+10; // 10 nappal léptetés előre d++; A fenti sorok nagyon jól mutatnak, de a + és a ++ operátorok nincsenek értelmezve a ‘Datum’ típusra.
3 class Datum { public int napokSzama; // ota public void Novel() { Novel(1); } public void Novel(int db) { napokSzama+=db; } } class Datum { public int napokSzama; // ota public void Novel() { Novel(1); } public void Novel(int db) { napokSzama+=db; } } Datum d = new Datum(” ”); d.Novel( 10 ); d.Novel(); Datum d = new Datum(” ”); d.Novel( 10 ); d.Novel(); A + és a ++ operátorok hiányában a probléma megoldható fv-ek írásával, de a kód sokkal csúnyább!
4 class Datum { public int napokSzama; // ota public static Datum operator+(Datum a, int b) { a.napokSzama = a.napokSzama+b; return a; } class Datum { public int napokSzama; // ota public static Datum operator+(Datum a, int b) { a.napokSzama = a.napokSzama+b; return a; } Datum d = new Datum(” ”); d = d+10; Datum d = new Datum(” ”); d = d+10; A + operátor overloading, hogy Datum és int között is értelmezve legyen!
5 Háromfajta operátor: Unáris: + - ! ~ Bináris: + - * / % && || ^ > == != >= Konverziós: C#-ban csak a már meglévő (fent felsorolt) operátorokat lehet újradefiniálni. Más nyelveken teljesen új operátort is be lehet vezetni. Nem lehet megváltoztatni az operátorok prioritását, csak azt lehet bővíteni, hogy milyen típusokra (típusok között) legyenek értelmezve.
6 Egyoperandusú operátor újradefiniálása: public static operator ( ) ‹ ER_TIPUS › az eredmény típusa, kötelezően ugyanaz, mint az osztály típusa ‹ OP › a következők egyike: + - ! ~ ‹ TIPUS › kötelezően ugyanaz, mint az osztály típusa ‹ NEV › a paraméter neve (szabadon választott) Ha pl. a ‘Datum’ típusra akarjuk kiterjeszteni valamelyik unáris operátor jelenetését, akkor a fenti ‘fv’-t szintén a Datum osztályba kell beleírni, az ‘ER_TIPUS’ és a ‘TIPUS’ is kötelezően ‘Datum’ kell legyen. Az unáris operátorok nem változtatják meg az eredeti típust!
7 class Datum { public int napokSzama; // ota public static Datum operator++(Datum a) { Datum x = new Datum(); x.napokSzama = a.napokSzama + 1; return x; } class Datum { public int napokSzama; // ota public static Datum operator++(Datum a) { Datum x = new Datum(); x.napokSzama = a.napokSzama + 1; return x; } Egyoperandusú ++ operátor újradefiniálása (példa): Datum d = new Datum(” ”); d++; Datum d = new Datum(” ”); d++; d = Datum.++(d);
8 class Datum { public int napokSzama; // ota public static Datum operator++(Datum a) { a.napokSzama ++; return a; } class Datum { public int napokSzama; // ota public static Datum operator++(Datum a) { a.napokSzama ++; return a; } Egyoperandusú ++ operátor újradefiniálása (példa): Datum d = new Datum(” ”); d++; Datum d = new Datum(” ”); d++; d = Datum.++(d);
9 Kétoperandusú operátor újradefiniálása: public static operator (, ) ‹ ERTIPUS › az eredmény típusa, tetszőleges típus lehet ‹ OP › a következők egyike: + - * / % stb… ‹ TIPUS1 ›, ‹ TIPUS2 › a kettő közül legalább az egyik a tartalmazó osztály típusa kell legyen ‹ NEV1 ›, ‹ NEV1 › a paraméterek neve (szabadon választott) Ha pl. a ‘Datum’ típusra akarjuk kiterjeszteni valamelyik bináris operátor jelenetését, akkor a fenti ‘fv’-t szintén a Datum osztályba kell beleírni, de az ‘ERTIPUS’ már bármi lehet (nem csak Datum). De a TIPUS1, TIPUS2 közül legalább az egyiknek ‘Datum’-nak kell lennie.
10 class Datum { public int napokSzama; // ota public static bool operator<(Datum a, Datum b) { if (a.napokSzama < b.napokSzama) return true; return false; } class Datum { public int napokSzama; // ota public static bool operator<(Datum a, Datum b) { if (a.napokSzama < b.napokSzama) return true; return false; } Kétoperandusú < operátor újradefiniálása (példa): Datum d1 = new Datum(” ”); Datum d2 = new Datum(” ”); if (d1<d2) … Datum d1 = new Datum(” ”); Datum d2 = new Datum(” ”); if (d1<d2) … If ( Datum. < ( d1, d2 ) ) …
11 class Datum { public int napokSzama; // ota public static int operator - (Datum a, Datum b) { return a.napokSzama-b.napokSzama; } public static Datum operator - (Datum a, int b) { a.napokSzama = a.napokSzama – b; return a; } class Datum { public int napokSzama; // ota public static int operator - (Datum a, Datum b) { return a.napokSzama-b.napokSzama; } public static Datum operator - (Datum a, int b) { a.napokSzama = a.napokSzama – b; return a; } Kétoperandusú - operátor újradefiniálása (példa): Datum d1 = new Datum(” ”); Datum d2 = new Datum(” ”); int x = d1-d2; Datum d3 = d1-10; Datum d1 = new Datum(” ”); Datum d2 = new Datum(” ”); int x = d1-d2; Datum d3 = d1-10; x = Datum. - (d1,d2) ; d3 = Datum. - (d1,10); x = Datum. - (d1,d2) ; d3 = Datum. - (d1,10);
12 Konverziós operátorok: - explicit: a programozónak jelölnie kell - implicit: automatikusan elvégzi a fordító public static implicit operator ( ) public static explicit operator ( ) public static implicit operator ( ) public static explicit operator ( ) ‹ ERTIPUS ›, ‹ TIPUS › a kettő közül legalább az egyik a tartalmazó osztály típusa kell legyen
13 class Datum { public static implicit operator int (Datum a) { return a.napokSzama; } class Datum { public static implicit operator int (Datum a) { return a.napokSzama; } Implicit Datum -> Int konverzió: Datum d = new Datum(” ”); int x = d+1; Datum d = new Datum(” ”); int x = d+1; x = Datum.implicit int (d) + 1;
14 class Datum { public static explicit operator int (Datum a) { return a.napokSzama; } class Datum { public static explicit operator int (Datum a) { return a.napokSzama; } Explicit Datum -> Int konverzió: Datum d = new Datum(” ”); int x = (int)d+1; Datum d = new Datum(” ”); int x = (int)d+1; x = Datum.explicit int (d) +1 ;