DictClass.extend()
nebo MSDN. Object definuje několik finálních metod (např.
handle()
) a čtyři překrytelné (equal()
, toString()
, wait()
a xml()
). Znamená to tedy, že každý objekt obsahuje tyto metody? Překvapivě… nikoli.Zkuste si vytvořit novou třídu, zkonstruovat její instanci a zavolat její metodu
toString()
. Takový kód vůbec nejde zkompilovat! Pokud tuto instanci přiřadíte do proměnné typu Object, přiřazení je sice korektní a Object obsahuje metodu toString()
, takže kompilace proběhne v pořádku, nicméně volání metody vyhodí runtime výjimku.Object o = new MyClass();
o.toString(); //runtime chyba
Metodu toString()
můžete ve své třídě sami naimplementovat a kód bude pochopitelně fungovat. Ale pozor - zde vytváříte nové metody, nepřekrýváte ty ze třídy Object. To má dva zřejmé efekty - zaprvé nemá smysl snažit se volat super()
(to platí i pro konstruktor(!)) a za druhé můžete vytvořit metodu stejné signatury jako má některá z finálních metod třídy Object.Chování, které byste asi očekávali od začátku, je nutné vynutit explicitním uvedením
extends Object
v classDeclaration
vaší třídy. Pak můžete na jejích instancích volat všechny metody zděděné z Object, překrytelné metody se objeví v kontextové nabídce (viz obrázek), můžete volat jejich implementaci ve třídě Object pomocí super()
a tak dále.Řešení pomocí
extends Object
používají zřejmě veškeré systémové třídy (tzn. třídy v
uvedené v System Documentation) a také některé třídy definované v X++, například RunBase.
Zajímavé je, že z pohledu Stromu aplikační hierarchie a DictClass tříd vypadají třídy s i bez
extends Object
zcela stejně. Popsané chování je také zcela v rozporu s MSDN dokumentací, která například říká: "Methods in the Object class can be called for any object.", tedy "Metody ve třídě Object mohou být volány pro libovolný objekt.".Zajímavých dopadů by se našlo jistě více, mě napadají tyto:
- Nelze vytvářet generickou funkcionalitu předpokládající, že všechny objekty v Axaptě mají určitou metodu (třeba
equal()
), protože to prostě není nijak zaručeno - Pokud není třída výslovně deklarována jako potomek Object, může implementovat i finální metody a ty budou zavolány (!!!). Takto lze například vracet libovolně zvolené číslo v
handle()
- a znamená to, že ani na finální metody třídy Object se nelze stoprocentně spolehnout.
extends Object
.
Žádné komentáře:
Okomentovat