Ich habe eine Frage zu einer Folie bei mir im Skript. Da steht nämlich folgendes:
Leider war ich an dem Tag nicht in der Vorlesung besucht und weiß nicht so genau was hiermit gemeint ist:
public boolean equals(Object obj)
1. nur mit meinem Typ vergleichen
2. downcast auf meinen Typ
3. meine Attribute vergleichen
Das ist aufjeden fall die Methode equals in der Klasse object.
Aber was meinen die mit punkt 1,2,3 *~*
Java:
Identität und Gleichheit==Operator prüft auf Identität
-Primitive: identischer Inhalt-Referenztyp: identische Referenz zum Speicher
equals inhaltliche GleichheitKlasse muss equals überschreiben (KlasseObject)Original equals in Objekt ist dasselbe wie ==publicbooleanequals(Object obj)1. nur mit meinem Typ vergleichen
2. downcast auf meinen Typ3. meine Attribute vergleichen
equals ist eine Äquivalenzrelation
seien x, y,z Objekte!=null1. reflexiv: x.equals(x) ist true2. symmetrisch: wenn x.equals(y)==true
dann gilt auch y.equals(x)==true3. transitiv: wenn x.equals(y)==true und y.equals(z)==true
dann gilt auch x.equals(z)==true(4.) x.equals(null) ist immer false====================
gleiche Objekte müssen denselben hashcode haben!!!=>MethodeinthashCode() muss überschrieben werden
Naja, mit equals legst du halt fest, wann deine Objekte inhaltlich gleich sind...da die Methode aber als Paramter ein Objekt als Object(also der Oberklasse) bekommt musst du das erstmal auf den Typen der Klasse bringen, um dann auf Methoden, Attribute etc. dieser Klasse zugreifen zu können...
1. bedeutet, dass wenn eben jmd deiner Klasse x, eine Instanz von y übergibt, das immer false ergeben soll, weil sie eben nicht die gleichen Typen haben, somit eben nicht gleich sein können...
Ich verstanden das wenn man ein Objekt der Oberklasse mit ein Objekt der Unterklasse nicht vergleichen kann. Deswegen muss man ein Downcast des objekts der Oberklasse auf die unterklasse machen und dann können die objekte verglichen werden.
Meinst du das?
ansonsten wärs sehr korrekt wenn du mir bitte ein beispiel geben könntest...
Du willst doch die Attribute deiner Klasse vergleichen..um das zu können, musst du eben Object downcasten!
Beispiel: (mal auf null-checks und ähnliches der Übersichtlichkeit verzichtet)
Java:
publicclassApfel{privateString sorte;@Overridepublicbooleanequals(Object obj){if(!(obj instanceofApfel)){returnfalse;}Apfel other =(Apfel) obj;if(!sorte.equals(other.sorte)){returnfalse;}returntrue;}}
Zuerst wird geprüft, ob obj überhaupt ein Apfel ist (mittels instanceof)
Danach erfolgt eben der Downcast, damit man danach halt auf das Attribut sorte zugreifen und vergleichen kann...ohne den Cast, wäre obj halt noch vom Typ Object..und Object hat nunmal kein Attribut sorte...
obj ist aber kein Apfel, deswegen erfolgt der downcast. Das ist völlig richtig. Aber der downcast wird nicht ausgeführt, da die Methode ja false zurück gibt. Und wenn false zurückgegeben wird dann wird der programmcode nicht weiter drunter ausgeführt. Soweit ich weis. Müsste man also nicht den downcast in einer anderen Methode machen, oder geht das so?
Und letzte frage... Die klasse Objekt hat kein Attribut namens sorte. Weswegen ist es bei dem vergleich dann so wichtig, das man obj downcastet. Warum erstellt man nicht einfach ein objekt der Klasse Apfel
also so:
Java:
Apfel neuesobjekt =newApfel();if(!sorte.equals(neuesobjekt.sorte))
oder man machts ohne ganz einfach:if(!sorte.equals(sorte))
obj ist aber kein Apfel, deswegen erfolgt der downcast. Das ist völlig richtig. Aber der downcast wird nicht ausgeführt, da die Methode ja false zurück gibt. Und wenn false zurückgegeben wird dann wird der programmcode nicht weiter drunter ausgeführt. Soweit ich weis. Müsste man also nicht den downcast in einer anderen Methode machen, oder geht das so?
Also das verstehe ich jetzt auch wieder nicht, was du damit meinst. Es kommt ja darauf an, mit welchem Objekt du das aufrufst, in der Regel rufst du das natürlich mit einem Objekt vom Typ Apfel auf!
Du willst ja schließlich die Äpfel vergleichen!
Java:
Apfel a =newApfel();Apfel b =newApfel();boolean sindGleich = a.equals(b);// b ist ja ein Apfel! Allerdings innerhalb der Methode erstmal noch nicht, da ist es dann ein Object...man muss daher downcasten !!!!
Und letzte frage... Die klasse Objekt hat kein Attribut namens sorte. Weswegen ist es bei dem vergleich dann so wichtig, das man obj downcastet. Warum erstellt man nicht einfach ein objekt der Klasse Apfel
also so:
Java:
Apfel neuesobjekt =newApfel();if(!sorte.equals(neuesobjekt.sorte))
oder man machts ohne ganz einfach:if(!sorte.equals(sorte))
Das macht ja beides keinen Sinn...wieso willst du ein neues Objekt erstellen? Das wäre ja dann immer gleich (oder auch nicht, also es würde halt immer das selbe Ergebnis liefenr, egal auf was, mit was man das aufrufen würde??) Ich glaube du verstehst die Methode an sich noch nicht..es ist nicht Ziel immer true zu erreichen..sondenr man will eben ein Objekt mit einem anderen (übergebenden) vergleichen.
So wie du das mit Strings auch machst
Java:
String a ="hallo";String b ="welt";boolean sindGleich = a.equals(b);//false ! Weil die Strings nicht gleich sind
(man könnte auch hier irgend ein Objekt übergeben)
man könnte als auch [c]"hallo".equals(new Apfel());[/c] schreiben..würde keinen Kompilerfehler geben, weil die Methode halt ALLE Objekte annimmt...Apfel lässt sich aber nunmal nicht zu String downcasten, weil die eben gar nichts mit einander zu tun haben, also vorher der Check !
Auch dein zweiter Vorschlag macht rein gar keinen Sinn, denn du vergleichst ja immer das selbe "sorte" ?!
obj ist ein Objekt der Oberklasse Object. Um aber die äquivalenz zu überprüfen muss man die Typen der der Objekte auf der selben Klasse bringen. Sprich obj muss vom Typ Apfel sein und other muss von Typ Apfel sein.
heisst das also auch ich könnte dann ebenfalls:
anstatt das hier
if (!sorte.equals(other.sorte)) {
auch folgendes schreiben:
if (!sorte.equals(obj.sorte)) {
wenn ich ein downcast vorgenommen habe das so aussähe: Apfel other = (Apfel) obj;
Weil hier wird ja obj von der Klasse Object in der Klasse Apfel downgecasted. Sprich der Typ von obj ist jetzt Apfe.
Ich hoffe du verstehst mich kleines problemschen bzw, hoffe es so richtig erklärt zu haben.
das sind nur die Zitate von denen ich meine Aussagen teilweise habe:
heisst das also auch ich könnte dann ebenfalls:
anstatt das hier
if (!sorte.equals(other.sorte)) {
auch folgendes schreiben:
if (!sorte.equals(obj.sorte)) {
wenn ich ein downcast vorgenommen habe das so aussähe: Apfel other = (Apfel) obj;
Weil hier wird ja obj von der Klasse Object in der Klasse Apfel downgecasted. Sprich der Typ von obj ist jetzt Apfe.
Nein eben nicht, obj ist immer noch Object Schreib`s doch mal in deine Entwicklungsumgebung...obj.sorte kennt er nicht, weil sorte wie oben schon erwähnt nun mal kein Attribut von Object ist !
Was ginge wäre
Java:
if(!sorte.equals(((Apfel)obj).sorte)){
Hier im Beispiel bei einem Attribut wäre das sogar imo okay, aber stell dir mal vor du hast nun mehr als ein Attribut, dann müsstest du vor jedem dieser immer casten..daher macht man das meistens einmal vorher
Apfel other = (Apfel) obj;
....
puh...vllt erkläre ich auch einfach nur richtig schlecht ?! Vllt kann wer anderes übernehmen dann =)
Der Compiler gibt ne Fehlermeldung aus. habs eigentlich verstanden aber bleibt wohl Phänomen. Weil ich bis heut imer dachte wenn ich ein Objekt der Oberklasse downcaste, das es in der Unterklasse die gleichen Rechte hat wie ein Objekt das von der Unterklasse erstellt worden ist.
und wenn ich dann nicht obj.sorte machen kann obwohls gedowncastet ist aber ( ( Apfel ) obj).sorte funktioniert dann is das komisch.
Trozdem danke, hab dich anscheinend einwenig zu sehr überbeschäftigt mit der erklärung.
Okay einen Versuch mache ich noch, dann bin ich im Bett...Das Objekt ist und bleibt die ganze Zeit ein Apfel!(es wurde ja schließlich irgendwann mal mit new Apfel() erzeugt. Nur lokal, für die Methode hat obj den Typ Object ! Es wurde also eingeschränkt)
Wenn du dann schreibst
Apfel other = (Apfel)obj;
änderst du nichts an der Referenz/Typ von obj.
Die neue Referenz, da weiß jetzt die Methode,: Ah Okay, other hat den Typ Apfel.
Vllt hilft dir das ja weiter(aber auch wirklich lesen ) :
Ja, um Antworten zu finden, die schonmal geschrieben wurden...
Einen 1-Jahr alten Thread wieder zu beleben nennt sich z.b. necro und ist nicht so toll
Wenn du keine Antwort findest, DANN mach nen neuen Thread mit deiner Frage.
Ich habe ein Problem mit dem Downcast.
Ich habe eine überarbeitete equals-Methode. Wenn ich ein Vergleich zweiter String Variablen durchführe, so bekomme ich ein ClassCastException. Warum?