Java-Rätsel und Überraschungen ;)

Objektorientierte Programmiersprache auf Basis einer virtuellen Maschine (https://www.oracle.com/java/)
Benutzeravatar
Xin
nur zu Besuch hier
Beiträge: 8858
Registriert: Fr Jul 04, 2008 11:10 pm
Wohnort: /home/xin
Kontaktdaten:

Re: Java-Rätsel und Überraschungen ;)

Beitrag von Xin » Fr Apr 19, 2013 11:57 am

nufan hat geschrieben:
Xin hat geschrieben:Ansonsten sagt mir der Quelltext auch nix mehr an möglichen Ungereimtheiten, die sich mit Java erklären ließen.
Du kannst das Programm ja mal starten und dich überraschen lassen ;)
Dafür muss ich erst mal Java installieren. ^^
Ähh... ja... ich habe das jetzt mal kurz überflogen und die erste Frage war "Wer kommt auf solche Ideen."

Der Entrüstung folgte schnell Ernüchterung: Ich komme auf solche Ideen. Ich habe eine Klasse "DebugMemory", bei der sich vor allem "ToString()" Funktionen bedienen. Die Klasse stellt X Speicherblöcke zur Verfügung, ToString nimmt sich einen und schreibt die Beschreibung eines Objektes rein. Diesen Text muss man dann kopieren. Kopiert man nur den Zeiger, so steht nach X Aufrufen von ToString() da eben was anderes drin...

Inzwischen gibt's bei mir aber auch eine String-Klasse, die das Problem einfacher löst. Damit löse ich dieses Konstrukt mehr und mehr ab... aber ich füge es nicht mehr nachträglich in Version 1.5 ein... Hallo!? Wenn ich das alleine mache, dann ist das ja mein private Blödheit, aber wenn ich das in eine Programmiersprache setze, die andere Leute benutzen, die ich darin schulen muss, damit sie damit keinen Mist bauen, dann muss ich Millionen Menschen schulen, damit die meine Bequemlichkeit beim Entwickeln der Sprache ausbaden müssen. Das bringt eventuell Leute um... und das ist ein abzusehendes Problem... Hallo!? Das darf man doch nicht veröffentlichen - und schon gar nicht als Feature... <kopfschüttel>
Merke: Wer Ordnung hellt ist nicht zwangsläufig eine Leuchte.

Ich beantworte keine generellen Programmierfragen per PN oder Mail. Dafür ist das Forum da.

sebix
Beiträge: 82
Registriert: Mo Nov 19, 2012 8:27 pm

Re: Java-Rätsel und Überraschungen ;)

Beitrag von sebix » Fr Apr 19, 2013 12:25 pm

[offtopic]
Du musst Java nicht installieren dafür, auf http://ideone.com/ kannst du dir Code kompilieren und laufen (sogar debuggen, aber hab ich noch nie probiert) lassen. Verwende ich des öfteren, wenn ich nur mal was kurz ausprobieren möchte :)

GilbertDur
Beiträge: 105
Registriert: Fr Mär 01, 2013 10:31 am

Re: Java-Rätsel und Überraschungen ;)

Beitrag von GilbertDur » Fr Apr 19, 2013 2:01 pm

Habs mal kompiliert. Da wär ich so von selbst nicht draufgekommen, bin auch kein Java-Nutzer. Es ist ein für mich wirklich seltsames verhalten :shock:

jeanluc
Beiträge: 33
Registriert: Mo Apr 22, 2013 10:18 pm

Re: Java-Rätsel und Überraschungen ;)

Beitrag von jeanluc » Mo Apr 22, 2013 11:55 pm

Ich versuche es zu verstehen und gleichzeitig zu erklären.

Die Schleife zählt i und j hoch. Rein intuitiv zählt sie bis MAX_INT hoch bis zu einer Exception kommt, allerdings gibt es ja die Abbruchbedingung.

Code: Alles auswählen

Integer.valueOf(i) == Integer.valueOf(j)


Der A == B Operator prüft in diesem Fall, ob Referenz A mit Referenz B identisch ist. Die Referenz zeigt auf den Speicherbereich wo das eigentliche Objekt liegt.

Da ist aber auch schon die Krux an dem Beispiel, denn Instanzen bzw. Objekte sollte man tunlichst nicht mit == vergleichen, dafür gibt es die equals() und compareTo() Methoden, die Objekte semantisch vergleichen.

Die Integer Klasse besitzt ein internes Caching, d.h. für die Repräsentation der Zahlen -127 bis +127 wird KEIN neues Objekt erzeugt, sondern die Referenz, die Integer.valueOf(int i) zurückgibt, ist in diesem Intervall immer die gleiche. Das spart CPU-Zeit und Arbeitsspeicher.

Siehe auch die Dokumentation:

Code: Alles auswählen

public static Integer valueOf(int i)
Returns an Integer instance representing the specified int value. If a new Integer instance is not required, this method should generally be used in preference to the constructor Integer(int), as this method is likely to yield significantly better space and time performance by caching frequently requested values. This method will always cache values in the range -128 to 127, inclusive, and may cache other values outside of this range.

Nachdem der Zustand i = 128 und j = 128 erreicht ist, folgt jedoch

Code: Alles auswählen

Integer.valueOf(128) != Integer.valueOf(128)
Warum ? Weil für i = 128 und j = 128 jeweils eine neue Instanz erzeugt wird. Es existieren jetzt zwei neu erzeugte und damit verschiedene Objekte mit unterschiedlichem Speicherort. Somit sind auch die Referenzen verschieden, die mit == verglichen werden. Abbruch.

Die gleiche Ausgabe lässt sich übrigens mit

Code: Alles auswählen

class Test {
 
  public static void main(String[] args) {
    for(int i = 0; Integer.valueOf(i) == Integer.valueOf(i); i++) {
      System.out.println("num: " + i);
    }
  }
 
}
erreichen.

Ich hoffe meine Erklärung ist richtig :)

Die Kritik von Xin ist hart. Dennoch: wo fängt Effizienz an und wo hört Wartbarkeit auf ? Wer auf Abstraktionen wie Java setzt (und dafür gibt es gute Gründe), muss mit solchen "Tunings" und Verhaltensmustern wohl leben.

Benutzeravatar
Xin
nur zu Besuch hier
Beiträge: 8858
Registriert: Fr Jul 04, 2008 11:10 pm
Wohnort: /home/xin
Kontaktdaten:

Re: Java-Rätsel und Überraschungen ;)

Beitrag von Xin » Di Apr 23, 2013 8:31 am

Moin Jeanluc!
jeanluc hat geschrieben:Die Kritik von Xin ist hart. Dennoch: wo fängt Effizienz an und wo hört Wartbarkeit auf ? Wer auf Abstraktionen wie Java setzt (und dafür gibt es gute Gründe), muss mit solchen "Tunings" und Verhaltensmustern wohl leben.
Nein, genau das sollte er eben nicht, denn Abstraktion bedeutet, dass man sich um Details keine Gedanken machen muss. Die Kritik muss eher härter ausfallen: Korrektheit ist immer wichtiger als Effizienz. Dazu muss der Entwickler aber möglichst intuitiv verstehen, was er tut und die Sprache muss sich möglichst demonstrativ richtig oder demonstrativ falsch verhalten.

Die Intuition sagt dem Entwickler, dass Integer.valueof(eins) == Integer.valueof(eins) ist und dass Integer.valueof( zweihundert ) == Integer.valueof( zweihundert ) ist. Im ersten Fall passt das, im zweiten passt es nicht. Aber nichtmals darauf kann man sich verlassen, es könnte ja auch True ergeben. Die Doku gibt das nicht her.

Auf diese Form von Abstraktionen darf man nicht setzen, denn Verwirrung ist keine Unterstützung dabei, qualitative Software zu schreiben. Wenn Integer.valueof( zweihundert ) == Integer.valueof( zweihundert ) immer falsch ist, dann ist das unintuitiv, aber begründbar. Es könnte ("may"(!)) aber auch true ergeben. Wenn sogar die Doku sagt, dass bei einer intuitiven(!) Lösung das Ergebnis nicht bestimmt ist, dann ist das nicht abstrakt, sondern willkürlich. Damit kann niemand qualitativ brauchbare Software herstellen - ganz besonders nicht Java-Entwickler, denn man muss die Intuitivität der Sprache ja auch nochmal mit dem Grund ihrer Entstehung in Verbindung bringen: Java wurde entwickelt, um billige Entwickler (in Ausbildung und Gehalt) zu ermöglichen, die trotzdem qualitativ wertige Software produzieren können.
Java war ein Marketing-Ballon, es war keine katastrophale Sprache, aber auch nie eine qualitative Sprache. Es ist lediglich in ihrer Zeit, in der sie entstanden ist, eine absolute Fehlkonstruktion.

Die Kritik kann und darf kaum freundlicher ausfallen.
Merke: Wer Ordnung hellt ist nicht zwangsläufig eine Leuchte.

Ich beantworte keine generellen Programmierfragen per PN oder Mail. Dafür ist das Forum da.

jeanluc
Beiträge: 33
Registriert: Mo Apr 22, 2013 10:18 pm

Re: Java-Rätsel und Überraschungen ;)

Beitrag von jeanluc » Mi Apr 24, 2013 3:18 pm

Xin hat geschrieben: Nein, genau das sollte er eben nicht, denn Abstraktion bedeutet, dass man sich um Details keine Gedanken machen muss. Die Kritik muss eher härter
ausfallen: Korrektheit ist immer wichtiger als Effizienz.
An welcher Stelle ist der Code denn nicht korrekt ? Jetzt kann man drüber streiten wie intuitiv eine Sprache sein muss, da bin ich bei dir, Java ist da kein Musterknabe. Nur Java ist da auch keine Ausnahme. Auf der anderen Seite, reden wir über die Sprache oder über die Bibliothek ? Es hindert ja niemanden daran, seine eigene Integer Klasse zu entwerfen und diese zu verwenden. Wer das nicht will, sollte die Klassendokumentation vor Benutzung lesen, und da springt einem das Verhalten von Integer.valueOf() sofort ins Auge.

Weiterhin: Der == Operator ist nicht für den Vergleich von Instanzen bzw. Objekten zu empfehlen, es sei denn man weiß warum, wieso und welche Referenzen man gerade vergleicht.

Dass du Willkür unterstellst halte ich für sachlich falsch. Das mit den billigen Programmierern lasse ich mal im Raum stehen.
Das was mich an Java eher nervt ist die Diktatur in dieser Sprache, man werkelt unter der Knute der OOP - und das für jeden kleinsten Kram.

Da werden dann für simpelste Aufgaben Entwurfsmuster herausgekramt und eine aufgeblähte Klassenhierarchie aufgebaut.
Ich kenne aber auch andere Standpunkte, besonders in größeren Projekten, da wird diese Diktatur sehr begrüßt.
Mit Software wie Jython (Python in Java) lässt sich diese Diktatur auch abmildern, wenn es denn gewollt ist.

Benutzeravatar
Xin
nur zu Besuch hier
Beiträge: 8858
Registriert: Fr Jul 04, 2008 11:10 pm
Wohnort: /home/xin
Kontaktdaten:

Re: Java-Rätsel und Überraschungen ;)

Beitrag von Xin » Mi Apr 24, 2013 3:50 pm

jeanluc hat geschrieben:
Xin hat geschrieben: Nein, genau das sollte er eben nicht, denn Abstraktion bedeutet, dass man sich um Details keine Gedanken machen muss. Die Kritik muss eher härter
ausfallen: Korrektheit ist immer wichtiger als Effizienz.
An welcher Stelle ist der Code denn nicht korrekt ? Jetzt kann man drüber streiten wie intuitiv eine Sprache sein muss
hehehe, natürlich ist der Code korrekt, er arbeitet ja so, wie in der Dokumentation beschrieben.
Die Frage ist, ob er das widerspiegelt, was der Programmierer wollte. Und die Sprache sollte dem Entwickler - imho - möglichst keine Stolperfallen geben.
jeanluc hat geschrieben:, da bin ich bei dir, Java ist da kein Musterknabe. Nur Java ist da auch keine Ausnahme.
Das ist korrekt. Allerdings gibt es Sprachen, die innovativ sind und neue Ideen vorantreiben - sich bei der Anwendung aber zeigt, dass die Anwender Features sie anders verwenden, als das die Entwickler sich das gedacht haben. Und es gibt Sprachen, die auf der Erfahrung mit anderen Sprachen aufbauen. Es ist immer ein großer Schritt nach vorne, der Innovation auslöst und dann ein Schritt zurück, der sich auf Standardtechniken konzentriert. Und Java hat sich auf teilweise sehr unsinnige Techniken konzentriert.

Mein persönliches Highlight war, als ich erkannte, dass sich das Fehlerverwaltung der Zukunft propagierte Exception-Management direkt mit dem COME FROM-Statement von Intercal herleiten lässt. Intercal ist eine Programmiersprache, die ausschließlich das kann, was man nicht verwenden sollte. COMEFROM ist ein umgekehrtes Goto. Man sagt nicht, wo man hinspricht, sondern man gibt an, wo man herkommt - wo man den Programmablauf unterbricht. Dieses Label definiert man in Java mit "throw".
jeanluc hat geschrieben:Auf der anderen Seite, reden wir über die Sprache oder über die Bibliothek ? Es hindert ja niemanden daran, seine eigene Integer Klasse zu entwerfen und diese zu verwenden. Wer das nicht will, sollte die Klassendokumentation vor Benutzung lesen, und da springt einem das Verhalten von Integer.valueOf() sofort ins Auge.
Wer immer sich auf die Disziplin von Programmierern verlassen muss, wird fehlerhafte Programme erhalten.
Du weißt ja sicher: Debuggen ist das Entfernen von Fehlern und Programmieren ist das Hinzufügen von Fehlern. Nimm dem Programmierer die Möglichkeiten Fehler einzufügen und Du erhältst bessere Programme.
jeanluc hat geschrieben:Das was mich an Java eher nervt ist die Diktatur in dieser Sprache, man werkelt unter der Knute der OOP - und das für jeden kleinsten Kram.

Da werden dann für simpelste Aufgaben Entwurfsmuster herausgekramt und eine aufgeblähte Klassenhierarchie aufgebaut.
"I had a problem and they said 'Use Java'. Now I have a problem factory"... ;-)
jeanluc hat geschrieben:Ich kenne aber auch andere Standpunkte, besonders in größeren Projekten, da wird diese Diktatur sehr begrüßt.
Mit Software wie Jython (Python in Java) lässt sich diese Diktatur auch abmildern, wenn es denn gewollt ist.
Auch hier wäre wieder die Frage, was OOP ist. Ich bin ein großer Befürworter von klassenbasierten Programmieren, datentyporientiertes Programmieren (was man als OOP versteht) sollte vermieden werden, sofern nicht erforderlich - was in Java mit "final" ausgedrückt wird. Ich persönlich bevorzuge es, erst etwas zu bestellen, bevor ich die Rechnung bekomme: "virtual" in C++. In Kombination mit override aus C# wird da eine gesunde Mischung draus, was in der aktuellen C++11 Version ja auch übernommen wurde.

Versteh mich nicht falsch - Java ist keine schlechte Sprache. Es gibt schlimmeres oder wie Du sagtest, Java ist keine Ausnahme. Wenn ich aber 1995 eine Sprache vorstelle, dann sollte es eine Sprache übertreffen, die 1982 vorgestellt wurde und durchdachter sein. Während sich C++ verhältnismäßig neutral verhält - also in der Regel der Programmierer entscheidet, ob er jetzt Mist baut oder lieber nicht, führt Java den Entwickler regelrecht in die Fehler, die es vermeiden sollte bzw. angeblich vermeiden wollte. Ich höre sie noch tönen, dass es in Java keine Pointer gibt, es gibt jetzt Referenzen! Dass Referenzen aber Null-Pointer-Exceptions auslösen, dass Java keine Daten einbetten kann, dass es keine C++-Referenzen gibt, das eigentlich alles aus C++ fehlt, womit man in C++ auf Pointer verzichten kann und dafür "Referenzen" verwendet werden, die genau das Problem erhalten, den man laut Marketing nicht mehr hat... das ist doch keine Weiterentwicklung?!
Ebenso die Umsetzung der Exceptions. Gut gemeint, aber leider nur dazu geeignet noch mehr Fehler zu machen.
Darum ist Java besser als vieles andere, aber trotzdem eine komplette Fehlkonstruktion.
Merke: Wer Ordnung hellt ist nicht zwangsläufig eine Leuchte.

Ich beantworte keine generellen Programmierfragen per PN oder Mail. Dafür ist das Forum da.

jeanluc
Beiträge: 33
Registriert: Mo Apr 22, 2013 10:18 pm

Re: Java-Rätsel und Überraschungen ;)

Beitrag von jeanluc » Mi Apr 24, 2013 4:45 pm

Fehlkonstruktion würde ich keinesfalls unterschreiben. Den Status Quo finde ich zufriedenstellend. Das Problem sehe ich eher bei den Entwicklern hinter und rund um Java. Allein die Spezifikation zu JPA, in die ich letztens reingeschaut habe, ist mit 250 Seiten dermaßen aufgebläht, dass man nur entnervt den Kopf schütteln kann. Zu viele Theoretiker, zu wenige Praktiker, die eine Sprache zu Tode planen.

Anderes Beispiel: Hibernate. Entwickler getroffen, die kein Plan von UNIX und SQL haben, sich aber in einem aufgeblähten Monstrum wie Hibernate pudelwohl fühlen. ORM ist schick, aber nicht immer sinnvoll. Egal: alles zu Objekten vergewaltigen, auch wenn hinterher keiner mehr durchblickt und der Code unwartbar geworden ist.

Benutzeravatar
Xin
nur zu Besuch hier
Beiträge: 8858
Registriert: Fr Jul 04, 2008 11:10 pm
Wohnort: /home/xin
Kontaktdaten:

Re: Java-Rätsel und Überraschungen ;)

Beitrag von Xin » Mi Apr 24, 2013 5:10 pm

Ich kommentiere mal nicht, ich lese rückwärts:
jeanluc hat geschrieben:alles zu Objekten vergewaltigen, auch wenn hinterher keiner mehr durchblickt und der Code unwartbar geworden ist.
jeanluc hat geschrieben:Hibernate. Entwickler getroffen, die kein Plan von UNIX und SQL haben, sich aber in einem aufgeblähten Monstrum wie Hibernate pudelwohl fühlen. ORM ist schick, aber nicht immer sinnvoll.
jeanluc hat geschrieben:Zu viele Theoretiker, zu wenige Praktiker, die eine Sprache zu Tode planen.
jeanluc hat geschrieben:die Spezifikation zu JPA, in die ich letztens reingeschaut habe, ist mit 250 Seiten dermaßen aufgebläht, dass man nur entnervt den Kopf schütteln kann.
jeanluc hat geschrieben:Fehlkonstruktion würde ich keinesfalls unterschreiben. Den Status Quo finde ich zufriedenstellend.
Welcher Quote passt nicht in die Reihe? Du ziehst bei Java über's Leder, dass es mir eine wahre Freude ist, aber beginnst, mit den Worten "Den Status Quo finde ich zufriedenstellend."
Häh?

Wenn Du bei Java genauso wie ich den Kopf schüttelst, warum bringst Du dann nicht "Java ist ein Griff ins Klo" über die Lippen bzw. die Tastatur? Zu viele Theoretiker, zu wenig Praktiker. Treffender kann man es nicht ausdrücken. Zu Tode gequält. Richtig - um nicht zu sagen, eigentlich noch nie praktisch lebensfähig gewesen. Jedenfalls nicht ohne Theoretiker und Marketing, die den Status Quo als zukunftsweisend deklarieren und damit Leuten, die nichts vom Programmieren verstehen erklärt haben, dass C++ böse und Java die Zukunft ist... und die Deppen haben das geglaubt, es waren ja auch keine Praktiker. Als ich Java an der Hochschule lernte, konnte mir mein Prof nicht erklären, wie man Java praktische Probleme sinnvoll löst - da habe ich aber auch schon 15 Jahre programmiert. Ich war immer "Praktiker".

Java war von Anfang an scheiße, ein großer Schritt in die vollkommen falsche Richtung.
Und wenn man so wie Du über Java spricht, dann darf man das Kind auch beim Namen nennen. Es ist eine Fehlkonstruktion für die Zeit in der es vorgestellt wurde. Wir hätten damals schon mindestens ein Stück weiter sein müssen, als wir im heutigen Alltag sind.

Java hat uns mindestens 20 Jahre gekostet, vermutlich wird es uns noch weitere 10 Jahre kosten.
Merke: Wer Ordnung hellt ist nicht zwangsläufig eine Leuchte.

Ich beantworte keine generellen Programmierfragen per PN oder Mail. Dafür ist das Forum da.

GilbertDur
Beiträge: 105
Registriert: Fr Mär 01, 2013 10:31 am

Re: Java-Rätsel und Überraschungen ;)

Beitrag von GilbertDur » Do Apr 25, 2013 9:09 am

Interessante Diskussion. Vor ner Weile habe ich mal die Meinung von einem Java-Fan gelesen(ich meine es war im Heise Forum) und er sagte: Wer programmiert denn noch Java ohne Frameworks. Das ist doch tödlich. Aber wenn man sich dann noch anschaut wie viele Java-Frameworks es inzwischen gibt und wie gut die meisten davon funktionieren...dazu die Release - und Sicherheitspolitik von Oracle...gute Nacht ;)

Antworten