# Was kann Java? Wofür benutzt man es?



## B4stl3r (7. Feb 2009)

Hallo!
Ich bin zurzeit "Programmiersprachen-hungrig" =)
Soll heißen: Ich habe HTML, CSS, C, C++, Delphi bereits gelernt (C und C++ nicht perfekt, ich weiß was Zeiger sind, kann Dateien auslesen und so aber mehr auch nich  )
Nun möchte ich die mächtige Sprache "Java" erlernen. Bevor ich anfange diese zu erlernen möchte ich eine grundlegende Frage wissen, die ich im Netz einfach nicht finden konnte.

Es wird überall geschrieben das Java für Websites und Softwarekomponente benutzt wird, DOCH nirgends steht wofür man es genau einsetzen kann. 

1.) Kann man damit z.b. ein Upload-Programm für Websites machen?
2.) Kann man vielleicht Spiele programmieren? Wenn ja 3D Spiele oder nur "Flash Games" ? (ich weiß mit c++ ist fürs Spieleprogrammieren die meistgebrauchte Sprache...is ja nur ne theorethische frage ^^)
3.) Könnte man z.b. Programme wie "Adobe Photoshop" (ich weiß sehr sehr viel Arbeit steckt dahinter...is ja nur theorethische frage ^^) oder ein Sicherheitsprogramm wie "norton antivirus" (ich weiß...fast unmöglich aber wie gesagt...sind nur theoretische Fragen)

Wenn ihr mir dies beantworten könntet wäre ich heilfroh!


----------



## Marco13 (7. Feb 2009)

_2.) Kann man vielleicht Spiele programmieren? Wenn ja 3D Spiele oder nur "Flash Games" ? (ich weiß mit c++ ist fürs Spieleprogrammieren die meistgebrauchte Sprache...is ja nur ne theorethische frage ^^)_
So theoretisch ist die garnicht: http://www.bytonic.de/html/jake2.html 

_3.) Könnte man z.b. Programme wie "Adobe Photoshop" (ich weiß sehr sehr viel Arbeit steckt dahinter...is ja nur theorethische frage ^^) oder ein Sicherheitsprogramm wie "norton antivirus" (ich weiß...fast unmöglich aber wie gesagt...sind nur theoretische Fragen)_
Ersteres schon, letzteres eher weniger - ein Antivirenprogramm braucht (vermutlich immer) HÖCHST spezifische Kenntnisse über das Betriebssystem - und genau die Notwendigkeit, diese Kenntnisse zu haben, will man mit einer Plattforumunabhängigen Sprache ja vermeiden.

Zu 1: Meinst du sowas FTP-Mäßiges? Java bietet von Natur aus viele "einfache" Möglichkeiten für "alles, was mit Netzwerken zu tun hat", aber bei einem Upload hat der Server ja noch ein Wörtchen mitzureden... (kenn mich' da nicht so aus)


----------



## B4stl3r (7. Feb 2009)

Ich danke für die Antwort

Zu 1.) Ich kenn mich da auch nich so aus aber einfach so ein Button auf z.b. ner homepage und da sucht man sich dann die datei vom rechner aus und loadet die hoch. sowas dürfte schon gehen oder?

danke für die anderen antworten! dann fang ich halt mal an mit java =)..hab gelesen da gibts keine pointer(zeiger)--> JUHU!!!


----------



## L-ectron-X (7. Feb 2009)

Wenn du das mit JSP/Servlets machen willst ist das in Ordnung. Applets wären auf jeden Fall die falsche Wahl.


----------



## Marco13 (7. Feb 2009)

B4stl3r hat gesagt.:
			
		

> danke für die anderen antworten! dann fang ich halt mal an mit java =)..hab gelesen da gibts keine pointer(zeiger)--> JUHU!!!



ALLES sind Zeiger  (außer den primitiven Datentypen). Aber man kann nicht den gleichen Mist damit machen, wie in C/C++, und alles, was daran "kompliziert" ist, ist "versteckt".


----------



## ice-breaker (7. Feb 2009)

B4stl3r hat gesagt.:
			
		

> Zu 1.) Ich kenn mich da auch nich so aus aber einfach so ein Button auf z.b. ner homepage und da sucht man sich dann die datei vom rechner aus und loadet die hoch. sowas dürfte schon gehen oder?



das ist doch HTML  :shock: 


```
<input type="file" name="Datei auswählen" />
```


----------



## Developer_X (7. Feb 2009)

ich kann dir nur sagen, 
Java ist eine objektorientierte Programmier Sprache


----------



## L-ectron-X (7. Feb 2009)

ice-breaker hat gesagt.:
			
		

> das ist doch HTML  :shock:


Ja und? Es gibt doch auch Java-Technologien für Webseiten.


----------



## hdi (7. Feb 2009)

> ALLES sind Zeiger



NICHTS sind in Java Zeiger. Es gibt nur Referenzen aber nicht das, was man als "Pointer" versteht.
Du arbeitest in Java also tatsächlich nur mit Objekten, und schiebst nicht irgendwelche Zeiger hin und her


----------



## Marco13 (7. Feb 2009)

Auch auf die Gefrahr hin, dass (mal wieder) ein Thread in eine philosophische Detaildiskussion abschweift: Eine Java-Referenz auf ein Objekt ist praktisch das gleiche wie ein C++-Pointer: Belegt ca. 4 bytes, kann null sein, oder auf einen "Speicherbereich" zeigen, wird by value an methoden übergeben... Dass man den nicht durch zeiger+=4 woanders hinschieben kann usw. hatte ich ja angedeutet. Zumindest eins ist sicher: Der Unterschied zwischen einer C++-Referenz und einer Java-Referenz ist größer als der Unterschied zwischen einem C++-Pointer und einer Java-Referenz


----------



## maki (7. Feb 2009)

> Es gibt nur Referenzen aber nicht das, was man als "Pointer" versteht.


Eigentlich sind Referenzen genau das, Zeiger ohne Arithmetik.

War wohl eine Marketing Entscheidung sie Referenzen zu nennen, wobei man dann konsequenterweise auch gleich eine NullReferenceException anstatt einer NullPointerException hätte haben sollen.


----------



## Guest (7. Feb 2009)

hdi hat gesagt.:
			
		

> > ALLES sind Zeiger
> 
> 
> 
> ...


Blödsinn, Pointer sind ebenso Referenzen, wie "Referenzen in Java". Du arbeitest in Java nicht mit Objekten, sondern mit Referenzen auf deine Objekte.
Wahrscheinlich "verstehst" du nur was falsches unter "Pointer".


----------



## 0x7F800000 (7. Feb 2009)

B4stl3r hat gesagt.:
			
		

> danke für die anderen antworten! dann fang ich halt mal an mit java =)..hab gelesen da gibts keine pointer(zeiger)--> JUHU!!!


In diesem Kontext klingt es eher so, als wärst du kein pointer-müder programmierer, der nach 10 Jahren Suche nach nirvana-zeigern die Schnauze voll hat, und sich deshalb auf Java freut, sondern viel mehr jemand, der nicht mal am Anfang Spaß an der Sache gefunden hat, d.h. überhaupt nie richtig gerafft hat, wozu die Zeiger da sind. :roll:

Und überhaupt, wenn deiner Meinung nach die Zeiger alles sind, was C++ ausmacht, dann hast du dich da wohl nicht allzu genau eingelesen: den Mist mit den Zeigern gibt's in C auch schon...

Also, ich find die Aussage einfach so merkwürdig... Als ich von C/C++ auf Java umgestiegen bin, da fühlte ich mich zwei Wochen lang erstmal so, als hätte man mir 9 Finger amputiert, nur wegen den fehlenden Zeigern :roll: deswegen find' ich die Reaktion etwas seltsam^^ ???:L


----------



## hdi (7. Feb 2009)

> Blödsinn, Pointer sind ebenso Referenzen, wie "Referenzen in Java".



Ja ich hätte mich vollständiger ausdrücken sollen, natürlich arbeitet Java _intern_ auch nur mit Zeigern auf den Speicher, so wie alles im Computer. 



> Du arbeitest in Java nicht mit Objekten, sondern mit Referenzen auf deine Objekte.


Das allerdings ist falsch. Java _selber_ arbeitet mit den Referenzen, aber _du_ nicht.
Wenn du den Namen eines Objekts hinschreibst, ist nämlich immer das Objekt *by value* gemeint, und keinesfalls
irgendeine Referenz/Pointer/nenn es wie du willst. Du arbeitest schlichtweg nicht mit Referenzen, das gibt's nicht.
Du arbeitest mit Objekten.

Du kannst mir kein Code-Beispiel geben, wo du mit einer Referenz arbeitest.


----------



## 0x7F800000 (7. Feb 2009)

hdi hat gesagt.:
			
		

> > Du arbeitest in Java nicht mit Objekten, sondern mit Referenzen auf deine Objekte.
> 
> 
> Das allerdings ist falsch. Java _selber_ arbeitet mit den Referenzen, aber _du_ nicht.
> ...


hö? ???:L 

```
public f(Object[] objects){
   for(Object o: objects){
      System.out.println(o.hashCode());
   }
}
```
"objects" ist da sicherlich nich "by value" übergeben, das sind definitiv alles referenzen. Es werden überall nur 4byte-lange referenzen hin und her geschoben, die jvm gibt sich sicherlich keine mühe, nur für so einen dämlichen funktionsaufruf das ganze array zu kopieren und by value in diese methode rüberzutransportieren, das wäre ein viel zu gigantischer aufwand, der eh fast nie nötig ist...

Okay, man könnte vielleicht sagen, dass durch "." alles sofort dereferenziert wird, und man "das eigentliche Objekt" vor sich hat... Aber kA, das ist doch jetzt alles Wortverdreherei, solang man weiß was es tut ist doch alles okay...


----------



## hdi (7. Feb 2009)

Ihr versteht mich falsch.
Was du machst ist


```
o.hashCode()
```

und damit arbeitest du auf dem Objekt o. Nochmal: Klar hat Java Referenzen, aber du als Programmierer
hast darauf keinen Zugriff. Du bennenst Objekte nach ihrem Namen, nicht nach ihrer Referenz.
Und du kannst nur die values von Objekten ändern, nicht irgendwelche Referenzen.

Komm schon, ihr wisst doch was ich meine?! Ich finde den Satz "arbeiten mit Referenzen" einfach
falsch in Java. Du kannst mit Referenzen nicht arbeiten, wie gesagt nicht mal was du in der Methode
übergibst ist für dich eine Referenz. Es ist auch nur ein Objekt (ein Array). Es ist halt NICHT ein 4-byte
Pointer, wie du es sagst. Das macht die JVM dann daraus, aber es ist das Objekt by value, das du dorthin
schreibst. Du kannst keine Referenz schreiben

edit: Um es vllt deutlicher zu machen: Wir programmieren in Java, so heisst die *Sprache*. 
Das ist nicht die JVM! Und in der Sprache java gibt es keine Referenzen.


----------



## Gast (7. Feb 2009)

Doch, jede Variable die du erstellst ist eine Referenz auf ein Objekt (gut, primitive sind wieder was anderes).
Das einzige was in Java nicht vorhanden ist, ist die aus C geliebte Pointerarithmetik wie die * und & Operatoren. Vielleicht bist du deswegen so verwirrt.


----------



## 0x7F800000 (7. Feb 2009)

hdi hat gesagt.:
			
		

> Komm schon, ihr wisst doch was ich meine?!


Ich weiß wie es da innendrin funktioniert und was mein code bewirkt. Wie du es nennst oder beschreibst ist mir daher vollkommen egal. Ich bin davon überzeugt, dass du das richtige meinst, nur imho sollte man aufhören zu versuchen das richtige zu _sagen_, und stattdessen einfach nur das richtige _denken_. 

Das ist wie in diesen Informatik-vorlesungen: der Prof steht da rum und erzählt zwei stunden lang irgendwas von "by value" und "by pointer" und "by reference", und die leute die das vorher nicht gerafft haben, wissen nachher genauso wenig, und sitzen da mit dem :bahnhof: Gesichtsausdruck.

Es ist doch ganz einfach: man lese sich die einzeiligen definitionen zu pointern und referenzen und zeigern durch, dann nehme man einen C-Compiler, und falle solange auf die Fresse, bis man es kapiert hat. Nach zwei Stunden ist das schwer ausformulierbare Wissen ohne den unnötigen Weg über das Sprachzentrum direkt in den Rückenmark rüberdiffundiert, und wird auch nicht mehr vergessen.



> Ich finde den Satz "arbeiten mit Referenzen" einfach falsch in Java.


Alles bis auf Primitive Datentypen wird in Java über Refernzen verwaltet und übergeben. Und ich meine, damit schonmal gearbeitet zu haben. Mir kommt deshalb der Ausdruck "arbeiten mit Referenzen" nicht falsch vor, kA was dich da so dran stört.


----------



## hdi (7. Feb 2009)

Hm..  :wink: 

Mir ist auch klar dass jeder hier das gleiche meint, aber es ist auch wichtig dass sich Leute richtig 
ausdrücken können, und nicht nur das richtige denken. Wenn das so wär, hätten wir ein Problem...

Ich starte noch einen Überzeugungsversuch:

Call-By-Reference ist ein englischer Ausdruck und bedeutet frei übersetzt "anwählen über einen Zeiger".
In C++ geht das: Ein dreizeiler schafft dir einen Buffer Overflow, und schon kannst du Inhalte
aus dem Speicher in dein Programm einbauen, die dort eigentlich nirgends definiert sind.
Du hast soeben etwas über eine Referenz im Speicher angewählt, Glückwunsch.

In Java g e h t  d a s  n i c h t.
Du kannst nichts ansprechen, dass du dir nicht vorher *als Objekt erstellt und benannt* hast.
Alles, was du irgendwo im Src reinschreibst, bennent einen Namen, den du vorher definiert hast.
Dieser Name steht für ein Objekt mit gewissen Inhalten, und nicht für einen Zeiger auf eine Stelle im Speicher.
Es ist Call-By-Value. 

Ich sag nochmal: Java ist eine Programmiersprache. Damit meint man das, was wir sehen. Man meint damit
nicht die Arbeit mit dem Hauptspeicher. Denn hier ist jedes Programm gleich: Alle 53148 Programmiersprachen
dieser Welt sind das selbe, und zwar Maschinencode die mit dem Speicher reden.

Aber das meint man nicht, wenn man von einer Sprache redet. Eine Sprache ist nach Definition eine Sammlung
von Wörtern und Grammatik. Referenzen gehören nicht zur Sprache Java, es gibt dieses Wort nicht und keine
Grammatik, die damit etwas tun kann.
EDIT: Achso wenn ich hier Referenzen sage, meine ich Pointer in c++!!

Also... ich find's falsch, einfach falsch. Mir egal was du denkst, wenn du mir sagst in JAva arbeitest du mit
Referenzen, dann denk ich mir "Ja du denkst das richtige, aber du hast gerade das falsche gesagt"  :bae:
Und zwar ist der Satz genau an der Stelle falsch geworden, wo du "Java" gesagt hast. Denn das ist eine Sprache.


----------



## Guest (7. Feb 2009)

hdi hat gesagt.:
			
		

> Mir ist auch klar dass jeder hier das gleiche meint, aber es ist auch wichtig dass sich Leute richtig
> ausdrücken können, und nicht nur das richtige denken. Wenn das so wär, hätten wir ein Problem...


nein, du denkst das falsche. Warum, steht weiter unten.



> Ich starte noch einen Überzeugungsversuch:
> 
> Call-By-Reference ist ein englischer Ausdruck und bedeutet frei übersetzt "anwählen über einen Zeiger".
> In C++ geht das: Ein dreizeiler schafft dir einen Buffer Overflow, und schon kannst du Inhalte
> ...


ist alles schön und gut, hat aber nichts mit dem Thema zu tun.



> Ich sag nochmal: Java ist eine Programmiersprache. Damit meint man das, was wir sehen.


Genau, und jede Variable die ich im Quelltext meines Programms schreibe und sehe ist eine Referenz (Primitive wieder ausgenommen)



> Referenzen gehören nicht zur Sprache Java, es gibt dieses Wort nicht und keine
> Grammatik, die damit etwas tun kann.


so langsam nervt's. Java kennt Referenzen. Bums Aus Nikolaus. Wenn du was anderes meinst lies dir die JLS durch http://java.sun.com/docs/books/jls/third_edition/html/j3TOC.html (Tipp: Strg+F Reference Enter)
Oder direkt der hier: http://java.sun.com/docs/books/jls/third_edition/html/expressions.html#15.21.3



> Und zwar ist der Satz genau an der Stelle falsch geworden, wo du "Java" gesagt hast. Denn das ist eine Sprache.


Ja und C (oder viel eher ein C-Programmierer) arbeitet mit Pointern. Beide Sätze korrekt.


----------



## hdi (7. Feb 2009)

Hey, du hast wohl geantwortet bevor ich eine Sache editiert hatte:

Aber das meint man nicht, wenn man von einer Sprache redet. Eine Sprache ist nach Definition eine Sammlung
von Wörtern und Grammatik. Referenzen gehören nicht zur Sprache Java, es gibt dieses Wort nicht und keine
Grammatik, die damit etwas tun kann.
EDIT: Achso wenn ich hier Referenzen sage, meine ich Pointer in c++!! 

..und jetzt sind wir uns einig, oder?

Es gibt in Java kein Wort, dass einen Pointer in C++ beschreibt

edit: Moment mal, ihr setzt ja C++ Pointer eben immer gleich mit Java Referenzen...
Hmm boah das wird anstrengend  Naja ich les mir mal deine Links durch und zieh bis dahin
den Kopf ein. Wenn alle etwas anderes darunter verstehen als ich, bin wohl eher ich im Unrecht.


----------



## hdi (7. Feb 2009)

Hm also in der JLS steht tatsächlich:


> 4.3.1 Objects
> An object is a class instance or an array.
> The reference values (often just references) are pointers to these objects



Für mich hört sich das so an, als ob Java tatsächlich Call-By-Reference arbeitet. 
Und dass das nicht stimmt, da sind wir uns ja alle einig.

Also ich komm grad echt total durcheinander :/ Was ist für die der Unterschied zwischen einer Referenz
und einem Pointer? Und was meinen sie mit "reference values", der Wert wofür? 

Okay, es sind Pointer ich kann ja machen

obj = a;
obj = b; // obj zeigt jetzt auf b

Aber wieso funktioniert das dann nicht bei der Übergabe in Methoden? Was wird DORT übergeben?

public void (Object obj) //<- was ist dann der Parameter? Referenz? Pointer? Wert? Hä?

Ist jmd so gnädig mich zu bekehren  Ich meine ich weiss wie es funktioniert, aber ich hab
da grad echt ein Begriffs-Wirrwarr in meinem Kopf. Für mich ist Pointer etwas, was ich mit C# in der uni
gelernt habe, und das es in Java nicht gibt.

Ich danke


----------



## 0x7F800000 (7. Feb 2009)

hdi hat gesagt.:
			
		

> Ich sag nochmal: Java ist eine Programmiersprache. Damit meint man das, was wir sehen. Man meint damit
> nicht die Arbeit mit dem Hauptspeicher. Denn hier ist jedes Programm gleich: Alle 53148 Programmiersprachen
> dieser Welt sind das selbe, und zwar Maschinencode die mit dem Speicher reden.
> 
> ...


Was soll dieses Blah jetzt?
In C++ gibt es einen sehr scharfen und klaren Unterschied zwischen call-by-value und call-by-reference.

Im ersten Fall wird auf dem Argument ein Copy-Konstruktor aufgerufen, und das ursprünglich übergebene Objekt bleibt von den manipulationen in der Methode auf jeden Fall unangetastet.

Im zweiten Fall wird die referenz auf das objekt übergeben, und alle änderungen in der methode sind auch draußen sichtbar.

Das sind zwei vollkommen verschiedene paar schuhe. Diese Sachen werden unterschiedlich geschrieben. Diese Sachen werden unterschiedlich ausgeführt. Da kannst du nicht mit irgendwelchen Sprüchen kommen, dass die Sprachsyntax an sich irgendwie von den Prozessen innendrin erstmal unabhängig wäre. In Java wird klar die zweite Möglichkeit verwendet. Wenn du mit den Werten des übergebenen Objektes arbeiten, aber das eigentliche Objekt "draußen" unangetastet lassen willst, hast du keine andere wahl, als innen in der Methode erstmal clone() aufzurufen, und dann erst mit diesem geklonten Objekt weiterzuarbeiten. Erst diese etwas umständliche Konstruktion würde dem C++ call-by-value in etwa entsprechen. In C++ hat der her Stoustrup den leuten diese paar Zeilen eben erspart...


----------



## 0x7F800000 (7. Feb 2009)

hdi hat gesagt.:
			
		

> Aber wieso funktioniert das dann nicht bei der Übergabe in Methoden? Was wird DORT übergeben?
> 
> public void (Object obj) //<- was ist dann der Parameter? Referenz? Pointer? Wert? Hä?


Referenz.



> Ist jmd so gnädig mich zu bekehren  Ich meine ich weiss wie es funktioniert, aber ich hab
> da grad echt ein Begriffs-Wirrwarr in meinem Kopf. Für mich ist Pointer etwas, was ich mit C# in der uni
> gelernt habe, und das es in Java nicht gibt.


call-by-value: methode kriegt eine komplette Kopie des übergebenen objektes, mit allen Gedärmen und member-variablen. Wird innen in der methode irgendwas an dieser Kopie geändert, so kriegt das Objekt draußen nichts von diesen veränderungen mit. In C++ wird das mit Copy-Konstruktoren umgesetzt. In Java gibt's das nur für primitive datentypen.

call-by-pointer: methode kriegt die Speicheradresse des Objektes. Alle veränderungen, die innen vorgenommen verden, werden direkt am übergebenen objekt vorgenommen, die methode greift ja direkt auf den speicher des Objektes zu. D.h. das übergebene Objekt "draußen" spürt alle Veränderungen, die an seinem Inhalt innerhalb der methode vorgenommen werden. In Java ist es "im prinzip so" nur dass man an die speicheradressen nicht willkürlich +1143 draufaddieren darf. In C++ ist das direkt möglich, da kriegt man wirklich die speicheradresse als "Zahl" übergeben.

call-by-reference: Tut praktisch dasselbe wie call-by-pointer. In C++ ist es so eine Art "verschleierte" call-by-pointer übergabe. Da wird genauso eine Speicheradresse des Objektes übergeben, allerdings sieht das rein Optisch einer call-by-value übergabe ähnlicher, d.h. man kann sich einen haufen nerviger "*"-Sternchen und "->"-Pfeilchen sparen. Aber man fummelt immer noch direkt am inhalt des "draußen" vorhandenen Objektes herum. In Java ist das alles immer "verschleiert", man kann da niemals +3243 auf einen zeiger draufaddieren, deswegen heißt es "call-by-reference" was ja auch sehr schön mit C++ zusammenpasst.

So... Hab ich das jetzt alles richtig und verständlich dargestellt? ???:L


----------



## byte (7. Feb 2009)

Nichts für ungut hdi, aber was Du hier in diesem Thread schreibst, ist absoluter Blödsinn. Vielleicht informierst Du Dich erstmal, bevor Du falsche Behauptungen aufstellst?

Natürlich gibt es in Java Referenzen und diese sind nichts anderes als Pointer (jedoch ohne Pointer Arithmetik). Es gehört zu den elementarsten Java-Grundlagen zu verstehen, wie Referenzen in Java funktionieren.

Foo obj = new Foobar();  <<< obj ist eine Referenz

Das, was man im allgemeinen unter Call By Reference versteht, gibt es in Java allerdings nicht, weil bei einem Methodenaufruf nicht die eigentliche Referenz übergebe wird sondern der "Reference-Value", also eine Kopie der Referenz.

doSomething(obj); <<< Referenz obj wird als Kopie übergeben (quasi ein Call by Reference-Value)

Damit werden solch unschöne Seiteneffekte verhindert, dass man ausserhalb des Scopes Zeiger (also Referenzen) umbiegen kann.


----------



## hdi (7. Feb 2009)

> Nichts für ungut hdi, aber was Du hier in diesem Thread schreibst, ist absoluter Blödsinn.


Ja das merk ich langsam 



> Vielleicht informierst Du Dich erstmal, bevor Du falsche Behauptungen aufstellst?


Hab mit bestem Wissen und Gewissen gepostet. Ich dachte, ich bin informiert...

...Ich hab irgendwann mal erfahren, es gäbe kein Call-By-Reference (siehe FAQ). Das der Effekt so ähnlich ist,
war mir durchaus klar. Ich dachte nur, da es kein Call-By-Reference gibt, gibt es auch keine Referenzen.
Ich meine dass es die intern gibt war mir schon immer klar, aber ich hielt den Begriff in Zusammenhang mit
Java nicht korrekt (deswegen vorhin mein "Blah" zur Sprache)



> doSomething(obj); <<< Referenz obj wird als Kopie übergeben



Call-by-Value auf einer Referenz, man kann also nur die Referenz nicht austauschen, weil es nur eine Kopie ist.
Sei zeigt aber wie das Original auf ein bestimmtes Objekt, und alle Änderungen wirken sich auch langfristig
auf das Objekt aus.

Okay, ich dachte bisher man übergibt nur Objekte, also Sammlungen von Werten, und man kann die Werte ändern,
aber nicht die "Sammlung" an sich. Und so ist es ja auch, nur halt die Begriffe waren mir nicht klar.

Also danke für die Erklärung  :###


----------



## B4stl3r (7. Feb 2009)

Andrey hat gesagt.:
			
		

> B4stl3r hat gesagt.:
> 
> 
> 
> ...



ich hab mit C angefangen und mit C++ mal reingeschnüffelt...ich meine ich bin erst junge 15 jahre...ich will nur ma wissen was ich zuerst angehe und sou ^^

kann ja in C und C++ nur bis Zeiger (einschließlich pointer)..sind zwar wichtige dinge aber einfach zum kotzn...die mag ich einfach nich..kA warum...

is halt meine meinung ^^...und in java gibt es keine pointer..in java nennt man sie referenzen (sind pointer-ähnlich) aber sie heißen halt referenzen....habs auf ca. 6 seiten nachgelesen ^^


----------



## 0x7F800000 (7. Feb 2009)

B4stl3r hat gesagt.:
			
		

> ich hab mit C angefangen und mit C++ mal reingeschnüffelt...ich meine ich bin erst junge 15 jahre...ich will nur ma wissen was ich zuerst angehe und sou ^^


c/c++ mit 15 ist schonmal nicht übel  :toll:



> kann ja in C und C++ nur bis Zeiger (einschließlich pointer)..sind zwar wichtige dinge aber einfach zum kotzn...die mag ich einfach nich..kA warum...


aah joo, das ist schon alles ganz witzig, man muss es nur einmal nachvollzogen haben


----------



## hdi (7. Feb 2009)

> aah joo, das ist schon alles ganz witzig



Pointer als "witzig" zu bezeichnen drückt dich irgendwie in eine Schublade mit Leuten,
die jedes C Programm pauschal so beginnen:


```
int main( int argc, const char* argv[] ){
   argv[0] = "sh";
   ...
```


----------



## Illuvatar (7. Feb 2009)

Vielleicht kann ich ja hdis Verwirrung noch ein Stückchen mehr entwirren:

Bei dem Ganzen by-value und by-reference Gerede gibt es theoretisch 2 Sachen, die gemeint sein könnten. (Also, ich rede von Objekten, nicht von Primitiven - dass die by-value übergeben werden ist ja klar):

Das eine ist sozusagen die eigentliche Variable. Die enthält nämlich im Endeffekt nur die Speicheradresse des Objektes, um das es geht. Davon kriegt man nur in Java exakt gar nichts mit.
Das andere ist das eigentliche Objekt, und darüber zu reden macht mehr Sinn. Die Sache ist jetzt allerdings die: Die "Speicheradresse" wird, genau wie ein primitiver Wert by-value übergeben. Das sieht man so:

```
public void foo(Object o) {
   o = something.else(); // In der aufrufenden Methode ändert sich nichts an der Variable
}
```

Viel interessanter ist aber, dass dadurch das eigentliche Objet "by-reference" übergeben wird:

```
public void bar(Changeable o) {
   o.change(); // Auch in der aufrufenden Methode wird o verändert!
}
```

In C# gibt es, nebenbei bemerkt, auch so etwas:

```
public void Foo(ref object o) { // in C# ist übrigens auch int etc. von object abgeleitet
   o = something.Else(); // Auch in der aufrufenden Methode ändert sich die Variable!
}
```


----------



## Marco13 (8. Feb 2009)

Ahh, da ist sie ja, die Diskussion. Auf manche Dinge kann man sich eben verlassen.

Nur so als Einwurf: Ich glaube, dass ein Großteil der Verwirrung und Worklauberei daher kommt, dass die Begriffe "Pointer" und "Referenz" für sich genommen nicht eindeutig sind. Man muss schon immer sagen, welche Sprache man meint. In C++ ist eine Referenz etwas GANZ anderes als in Java. (Dafür gibt's in C++ Referenzen auf Pointer )


----------



## 0x7F800000 (8. Feb 2009)

Illuvatar hat gesagt.:
			
		

> ```
> public void Foo(ref object o) { // in C# ist übrigens auch int etc. von object abgeleitet
> o = something.Else(); // Auch in der aufrufenden Methode ändert sich die Variable!
> }
> ```


und "Type** ppZeigerszeiger" gab's wofür? ???:L Die syntax war zumindest konsistent und verständlich... Weiß jetzt nicht inwiefern "ref type name" eine verbesserung davon sein soll... :roll: aber gut, kA von C# da braucht ihr mich jetzt nicht davon zu überzeugen wie toll es mit "ref Type name" ist...



> In C++ ist eine Referenz etwas GANZ anderes als in Java


Du meinst jetzt also die "nicht-C++-pointer-sondern-c++-referenz" und die "stinknormal-java-referenz"?
okay... hdi ist jetzt glaub ich mal fertig, aber was ist jetzt an einer C++ referenz so viel anders als in java-referenz? jetzt fängt bei mir der bahnhof-zustand an :shock:

edit: äääh, ne, alles richtig, mich hat jetzt nur deine formulierung kurzfristig voll verwirrt. was ich vorhin geschrieben hab trifft auch nicht so wirklich zu, auch wenn sich referenzen in c++ bei argumenten ähnlich verhalten, wie die java-referenzen. 

Aber welchem c++ ding würden die java-referenzen also entsprechen? ???:L Die sehen doch in etwa aus wie c++ referenzen, aber verhalten sich eigentlich fast genauso wie c++ zeiger... Wieso nennst du die referenzen auf zeiger? :bahnhof:

oh ne leute, ehrlichgesagt: ich will's gar nich wissen, sonst wach ich in ~6 stunden auf und weiß nicht mehr was in java 'ne referenz ist :autsch: Das ist alles nur total verwirrend.


----------



## B4stl3r (8. Feb 2009)

Da hab ich ja eine schöne Diskussion eröffnet xD

is ja egal...in c/c++ gibts zeiger und referenzen (fast das gleiche) und in java halt nur referenzen und fertig ^^


----------



## maki (8. Feb 2009)

> in c/c++ gibts zeiger und referenzen (fast das gleiche) und in java halt nur referenzen und fertig ^^


Die Erklärung ist zwar falsch, stimme dir aber zu dass genug über Dinge diskutiert wurde die eigentlich klar sind.


----------



## Marco13 (8. Feb 2009)

_.in c/c++ gibts zeiger und referenzen (fast das gleiche)_

Nee, ist schon ein ziemlicher Unterschied. IMHO.



			
				Andrey hat gesagt.:
			
		

> > In C++ ist eine Referenz etwas GANZ anderes als in Java
> 
> 
> Du meinst jetzt also die "nicht-C++-pointer-sondern-c++-referenz" und die "stinknormal-java-referenz"?
> ...



OK, ich antworte trotzdem - vielleicht schaff' ich es ja, Aussagen zu machen, die einfach UND präzise sind...:

Ein C++-Pointer ist eine Variable, die als Wert einen Speicherbereich enthält. Ein C++-Pointer enthält als Wert also den Speicherbereich, an dem das Objekt steht, auf das - bildlich gesprochen - der C++-Pointer zeigt.


```
// Eine (nicht funktionierende!) Swap-Funktion für C++-Pointer:
// Die Pointer werden BY VALUE an diese Funktion übergeben
void swap(Foo *x, Foo *y)
{
    Foo *temp = x;
    x = y;
    y = temp;
}

Foo *a = new Foo(1); // a ist ein Zeiger auf die Stelle, an der das neue Foo(1) liegt
Foo *b = new Foo(2); // b ist ein Zeiger auf die Stelle, an der das neue Foo(2) liegt

// Ein swap, das nicht funktioniert:
swap(a,b);

print(a->value); // Gibt immernoch "1" aus
print(b->value); // Gibt immernoch "2" aus

// Zuweisung
a = b; // a zeigt jetzt auch auf die Stelle, an der Foo(2) liegt (und man hat ein Memory leak :wink: )

print(a->value); // Gibt jetzt "2" aus

b = NULL;
print(b->value); // Kracht
```


Abgesehen von Zeigerarithmetik, **zeigerZeigern und anderen Zaubereien ist eine Java-Referenz genau das gleiche. Man kann sie auf verschiedene Objekte "zeigen" lassen, ohne dass die Objekte davon beeinflusst werden. Wenn man den Wert der Java-Referenz verändert, verändert sich das Objekt nicht. Java-Referenzen werden (wie die C++-Pointer oben) immer BY VALUE an Methoden übergeben. Der obige Code läßt sich also leicht nach Java übersetzen:

```
// Eine (nicht funktionierende!) Swap-Funktion für Java-Referenzen
// Die Referenzen werden BY VALUE an diese Funktion übergeben
void swap(Foo x, Foo y)
{
    Foo temp = x;
    x = y;
    y = temp;
}

Foo a = new Foo(1); // a ist eine Java-Referenz das neue Foo(1) 
Foo b = new Foo(2); // a ist eine Java-Referenz das neue Foo(2) 

// Ein swap, das nicht funktioniert:
swap(a,b);

print(a.value); // Gibt immernoch "1" aus
print(b.value); // Gibt immernoch "2" aus

// Zuweisung
a = b; // a referenziert jetzt auch auf das Foo(2)

print(a.value); // Gibt jetzt "2" aus

b = null;
print(b.value); // Kracht
```

Langweilig - im eigentlichen Code wurde nichts geändert, außer dass alle "*" Sternchen weggenommen wurden, und die Dereferenzierungen von "a->value" zu "a.value" geändert wurden.

Das interessante ist, das der Code sich prinzipiell noch genauso verhält: Wie auch in der C++-Version ist die Ausgabe
1,2,2. Wie auch in der C++-Version funktioniert das "swap" nicht. Alles ist perfekt analog zur C++-Version mit C++-Pointern.


Im Vergleich dazu gibt's in C++ aber auch Referenzen. Die werden meistens für Argumente von Methoden verwendet (eben um "call by Reference" zu ermöglichen) aber manchmal auch als "Abkürzungen" für andere Objekte.


```
// Eine (funktionierende!) Swap-Funktion für C++-Pointer:
// Die Pointer werden BY REFERENCE an diese Funktion übergeben.
// Foo& *x ist eine Referenz auf einen Pointer
void swap(Foo& *x, Foo& *y)
{
    Foo *temp = x;
    x = y;
    y = temp;
}

Foo *a = new Foo(1); // a ist ein Zeiger auf die Stelle, an der das neue Foo(1) liegt
Foo *b = new Foo(2); // b ist ein Zeiger auf die Stelle, an der das neue Foo(2) liegt

// Ein swap, das funktioniert:
swap(a,b);

print(a->value); // Gibt "2" aus
print(b->value); // Gibt "1" aus
```

Eine C++-Referenz ist also etwas (ganz) anderes als ein C++-Pointer oder eine Java-Referenz:
C++-Pointer und Java-Referenzen sind praktisch "Variablen, die als Wert eine Beschreibung haben, an welcher Stelle ein Objekt liegt". Man kann mit Hilfe dieser Variablen leicht auf den Speicherbereich zugreifen, an dem die Objekte liegen. Und man kann sie auf andere Stellen zeigen/referenzieren lassen.
Eine C++-Referenz ist (sozusagen) KEINE Variable, sondern nur ein NAME. Lokal braucht eine C++-Referenz eigentlich keine "physische Repräsentation" zu haben. Da ist sie nicht viel mehr als eine "Abkürzung" - ein "Alias" für irgendwas anderes. Praktisch z.B. bei sowas wie

```
vector<Foo> fooVector;
...
Foo& b = fooVector[123]; // "Abkürzung" 
b.value = 666;
...
print(fooVector[123].value); // Gibt 666 aus
```

Hoffentlich habe ich damit nicht mehr Ungenauigkeiten in den Thread eingebracht, also vorher schon da waren. Hm.


----------



## B4stl3r (8. Feb 2009)

Marco13 hat gesagt.:
			
		

> _.in c/c++ gibts zeiger und referenzen (fast das gleiche)_
> 
> Nee, ist schon ein ziemlicher Unterschied. IMHO.



schon klar aber es hat eine gewisse ähnlichkeit. ziemlicher unterschied nenn ich ne website und ne kartoffel ^^

pointer und referenzen sind ähnlich sagen wa so


----------



## 0x7F800000 (8. Feb 2009)

B4stl3r hat gesagt.:
			
		

> ziemlicher unterschied nenn ich ne website und ne kartoffel ^^


joah, wenn man das jetzt etwas allgemeiner sieht, dann hast du sowas von Recht :lol: :toll:


----------



## andre111 (11. Feb 2009)

:shock:


----------



## Spacerat (11. Feb 2009)

Ich hätte da einen gravierenden Unterschied: Java-Objekte haben im Gegensatz zu C++-Objekten einen Overhead. Während in C++ eine Referenz auf ein Objekt meistens auch gleich die Referenz auf den 1. Member dieses Objekts (vgl. Array) ist, hat man in Java eben nur eine Referenz auf das Objekt. In Java gibt es deswegen z.B. auch kein "sizeof", weil z.B. ein Obkekt des Typs String mit 11 Zeichen, anders als in C++, definitiv länger als 11 Bytes ist.

mfg Spacerat


----------



## Ebenius (11. Feb 2009)

Spacerat hat gesagt.:
			
		

> Ich hätte da einen gravierenden Unterschied: Java-Objekte haben im Gegensatz zu C++-Objekten einen Overhead.


Hmm... Das kann eigentlich nicht stimmen. Nicht dass ich das wüsste... Aber wie würden denn virtuelle Methodenaufrufe in C++ realisiert, wenn es exakt keine Zusatzinformation am Objekt gäbe?

Ebenius


----------



## Spacerat (11. Feb 2009)

Das stimmt aber... Letztendlich muss man sich vor Augen führen, was aus C++ Quelltext nach dem kompilieren wird. Ich habe oben nicht ohne Sinn von Membern allgemein gesprochen. Diese Member können durchaus auch Methoden sein. Methoden in C++ sind durchweg Pointer auf ausführbaren Assembler-Code (Function-Pointer). Methoden-Parameter werden entweder auf den Stack gelegt oder in Register geschrieben.

mfg Spacerat


----------



## Ebenius (11. Feb 2009)

Spacerat hat gesagt.:
			
		

> Diese Member können durchaus auch Methoden sein. Methoden in C++ sind durchweg Pointer auf ausführbaren Assembler-Code (Function-Pointer).


So ein Unsinn. Referenzen auf Methoden können bei nicht-virtuellen Methoden direkte Sprünge sein. Virtuelle Methoden werden immer über eine VMT (oder ein vergleichbares Konstrukt) referenziert!


			
				Spacerat hat gesagt.:
			
		

> Methoden-Parameter werden entweder auf den Stack gelegt oder in Register geschrieben.


Das ist grad noch mehr Unsinn, da es mit der Sprache absolut nichts zu tun hat, sondern lediglich vom Compiler und der Zielmaschine abhängt.

Nachtrag:


			
				Spacerat hat gesagt.:
			
		

> Ich habe oben nicht ohne Sinn von Membern allgemein gesprochen.


Doch. "Ohne Sinn" trifft's ganz gut. Du hast oben auch von String-Klassen gesprochen die seltsamer Weise genau ein Byte pro Zeichen benötigen. Nicht einmal nullterminiert sind sie. Und eine Längenangabe gibt's auch nicht. ???:L So what?

Ebenius


----------



## Spacerat (11. Feb 2009)

@Ebenius: Jetzt hast du mich aber da liegen LLLOOOOLLLL...
Von was für Zielsystemen reden wir hier? Haben deine verschiedenen Zielsysteme verschiedene Prozessoren? Dann hast du möglicherweise recht. Bei 68k-, PPC-, x64- und x86-Prozessoren ist es jedenfalls wie oben beschrieben.
Hab' ich villeicht den Fehler gemacht und das obige auf C++ spezifiziert? Dann verbesser' ich das mal. Jede Kompilersprache, deren Kompiler keinen speziellen Bytecode (wie z.B. Java) produzieren, produzieren Maschinen-Code. Und auf dieser Basis ist es völlig "Hupe", wie eine Funktion aufgerufen wird, es bleibt eine Sprungadresse. Und Parameterübergabe in Assembler funktioniert eben auch nur wie oben beschrieben (Stack oder Register).

Nachtrag: Nein "sizeof" gibts in Java immer noch nicht.

mfg Spacerat


----------



## byte (11. Feb 2009)

Spacerat hat gesagt.:
			
		

> Und auf dieser Basis ist es völlig "Hupe", wie eine Funktion aufgerufen wird, es bleibt eine Sprungadresse.


Wie soll der Compiler bitte direkte Sprungadressen anlegen, wenn die eigentlichen Aufrufe polymorph sind? Das läuft über vtables.



> Nachtrag: Nein "sizeof" gibts in Java immer noch nicht.


Ist auch etwas schwierig in einer plattformunabhängigen Sprache, meinst Du nicht?




> Diese Member können durchaus auch Methoden sein. Methoden in C++ sind durchweg Pointer auf ausführbaren Assembler-Code (Function-Pointer).


Auch in Java sind Methoden einfache Funktionspointer. Methoden werden vom Classloader initial geladen und in der Method Area abgelegt. Sie haben überhaupt nichts mit dem Objektzustand zu tun und beeinflussen natürlich auch nicht die Größe eines Objekts im Heap.


----------



## Spacerat (11. Feb 2009)

byto hat gesagt.:
			
		

> Wie soll der Compiler bitte direkte Sprungadressen anlegen, wenn die eigentlichen Aufrufe polymorph sind? Das läuft über vtables.


Klar... hab' auch nirgendwo geschrieben das der Kompiler das macht, lediglich das es letztendlich nur Sprungadressen sind (Aufrufbar mit "JMP" oder "JSR").


			
				byto hat gesagt.:
			
		

> Ist auch etwas schwierig in einer plattformunabhängigen Sprache, meinst Du nicht?


Sag' das nicht mir...


			
				byto hat gesagt.:
			
		

> Auch in Java sind Methoden einfache Funktionspointer. Methoden werden vom Classloader initial geladen und in der Method Area abgelegt. Sie haben überhaupt nichts mit dem Objektzustand zu tun und beeinflussen natürlich auch nicht die Größe eines Objekts im Heap.


Natürlich landet man auch in Java irgendwann zwangsläufig auf der Assembler-Basis. Zwischen "Java" und "Assembler" liegt aber stets die JVM, in welcher die referenzierten Objekte eben den erwähnten "Overhead" haben.

mfg Spacerat


----------



## Ebenius (11. Feb 2009)

Spacerat, lies Dir einfach mal Deine ersten beiden Posts auf der letzten Seite durch und dann versuch mal zu verstehen, was ich daran zu kritisieren hatte. Natürlich wird letztlich bei einem Methodenaufruf irgendwann mit irgendeinem Jump irgendwo hingesprungen. Was Du aber oben schreibst ist und bleibt falsch. In C++ haben Objekte Overhead. Sie müssen Overhead haben, um virtuelle Methoden abbilden zu können. Um nichts anderes ging es mir.


----------



## Guest (11. Feb 2009)

wenn du C, Assabler Objecte in Java aufrufst ensteht ein Overead, das ist richtig.
Das lieg aber nicht an der JVM, sonder an JNI. Da Java die Zeiger auf die C-Methoden kennen muss, müssen (weitere) wrapper her, diese erzeugen einen erheblichen Overhead. Bei echtzeitprogrammen (Spielen) macht sich das start in der Framerate bemerkbar.
Genaue werte hab ich nicht im Kopf, aber schafft ein C Programm 100fps kannst du über JNI ca. 20-30% bzw. frames abziehen (durch den JNI-overhead)


Solange du aber reine Java-Programme schreibt, das heisst; du lässt C völlig weg, entsteht kein overhead, da nur referenzen übergeben werden.

Die Referenz-Adresse lässt sich auch (super-)leicht mit System.out.println(object); ausgeben.

Mir ist es noch nie passiert, das dort Bytecode ausgegeben wird.
Fazit: Es sind referenzen.


----------



## byte (11. Feb 2009)

Anonymous hat gesagt.:
			
		

> Die Referenz-Adresse lässt sich auch (super-)leicht mit System.out.println(object); ausgeben.
> 
> Mir ist es noch nie passiert, das dort Bytecode ausgegeben wird.
> Fazit: Es sind referenzen.


 :autsch:


----------



## Spacerat (11. Feb 2009)

Ebenius hat gesagt.:
			
		

> Was Du aber oben schreibst ist und bleibt falsch. In C++ haben Objekte Overhead. Sie müssen Overhead haben, um virtuelle Methoden abbilden zu können.


Ich bleibe dabei und das ist keine Böswilligkeit: Diese Overheads haben C++-Objekte nur zur Kompile-Zeit. Nach dem Linken sind sie jedenfalls geschichte. In Java dagegen bleiben sie auch zur Laufzeit erhalten. Und genau darum ging es mir.

mfg Spacerat


----------



## Ebenius (11. Feb 2009)

Spacerat hat gesagt.:
			
		

> Ebenius hat gesagt.:
> 
> 
> 
> ...


Und genau dort verstehe ich's nicht. Auch von mir keine Böswilligkeit. Dann erklär mir bitte wie virtuelle Methodenaufrufe in C++ umgesetzt werden! Schon per Definition kann man dabei nicht zur Compile-Time binden. Warum gehst Du auf diese Frage nicht ein?

Ebenius


----------



## Ice-Tea (11. Feb 2009)

Ich hab da grad was schönes zu gefunden:
Sie werden jetzt vielleicht fragen, weshalb dieses mächtige Werkzeug – man spricht auch von später Bindung (late binding), weil die Zuordnung von Methodenname zu Implementation erst zur Laufzeit vorgenommen wird – mit einem Schlüsselwort extra „eingeschaltet“ werden muss. Polymorphie verursacht mehr Verwaltungsaufwand für das Laufzeitsystem: Objekte einer polymorphen Klasse müssen einen „Rucksack“ mit Funktionszeigern (die so genannte virtual function table) mit sich herumtragen, und jeder Methodenaufruf erfordert eine zusätzliche Zeigerdereferenzierung.
C++ Programmierung: Polymorphie


----------



## Spacerat (11. Feb 2009)

Das hat "byto" schon geschrieben. Das ganze läuft über sogenannte "vtables" (sozusagen ganze Tabellen solcher Funktionspointer). Das ganze heisst dann indirekte Adressierung.

Das was Ice-Tea dort schreibt ist auch nur bis zum Link-Vorgang interessant. In Assembler müssen ausschliesslich Funktionspointer von DLLs vor der Ausführung initialisiert werden. In C++ wird dazu das Schlüsselwort "extern" verwendet.

Nachtrag: Villeicht ist es letztendlich noch hilfreich, zu erwähnen, dass Assembler eine strukturierte und keine Objektorientierte Sprache ist.

mfg Spacerat


----------



## Ebenius (11. Feb 2009)

Spacerat hat gesagt.:
			
		

> Das hat "byto" schon geschrieben. Das ganze läuft über sogenannte "vtables" (sozusagen ganze Tabellen solcher Funktionspointer). Das ganze heisst dann indirekte Adressierung.


Ist mir bekannt. Es heißt VMT oder VTable wie ich oben schon schrieb. Um das zu benutzen muss eben das Objekt Overhead herumtragen. Genau das sag ich doch. :roll:

Ebenius


----------



## Marco13 (11. Feb 2009)

Ohne das ganze Gekloppe jetzt nachvollzogen zu haben:


			
				Spacerat hat gesagt.:
			
		

> Ich bleibe dabei und das ist keine Böswilligkeit: Diese Overheads haben C++-Objekte nur zur Kompile-Zeit. Nach dem Linken sind sie jedenfalls geschichte. In Java dagegen bleiben sie auch zur Laufzeit erhalten. Und genau darum ging es mir.



Das stimmt für Java weniger als für C++. In C++ wird alles einmal compiliert. Polymorphe Aufrufe werden über die VTable gemacht. OB da ein Linker was dran dengeln kann, weiß ich nicht. Aber in Java kann definitiv was dran gedengelt werden: Da kann nämlich mittendrin der Just-In-Time-Compiler zuschlagen - der kann erkennen, OB ein Aufruf wirklich Polymorph ist (d.h. ob eine Methode überschrieben wurde), und wenn der Aufruf NICHT Polymorph ist, einfach die "VTable" in den Müll werfen und den polymorphen Aufruf durch einen Monomorphen (also direkten) Aufruf ersetzen. Zusätzlich unterscheidet Java auch noch zwischen Monomorphismus, Bi-Morphismus und Polymorphismus, wobei Bi-Morphismus nochmal "optimiert" ist - näheres dazu auch unter http://www.javaspecialists.eu/archive/Issue158.html


----------



## Spacerat (12. Feb 2009)

Das wirft meinen Standpunkt aber nun nicht um, sondern bestärkt ihn nur. (BTW: Mittlerweile nehme ich an, das wir aneinander vorbei reden...). In dem Overhead einer Java-Methode muss z.B. noch stehen, ob diese "private", "protected" oder wie auch immer ist, welche Parameter zur Ausführung nötig sind usw (Methoden-Signatur). In "vtables" liegen ausschliesslich Adressen. Will sagen, in einer Ausfürbaren Datei aus C++ entfallen diese Abfragen, weil sie vom Kompiler oder Linker bereits erkannt und eliminiert bzw. optimiert wurden. Deswegen würde ich diese "vtables" nicht als Overhead im Sinne von Java-Overheads bezeichnen.

mfg Spacerat


----------



## Ebenius (12. Feb 2009)

Tut mir leid, Spacerat, die VMT existiert zur Laufzeit oder gar nicht. Sobald Virtuelle Methodenaufrufe existieren, können diese nur zur Laufzeit ausgewertet werden. Anders geht es nicht.

Ebenius


----------



## Spacerat (12. Feb 2009)

Mir tuts auch Leid... Aber ein Assembler-Crash-Kurs, der euch darlegt worauf ich hinaus will, führt zu weit, finde ich. Ist auch recht müssig, sich über die Unterschiede von Overheads in Java und VMTs die manche auch als Overhead bezeichnen, auseinanderzusetzen.  Deswegen... Keine weiteren Ausführungen.

mfg Spacerat


----------



## Gast (12. Feb 2009)

Wie du in jedem Thread Mist labern musst, genau wie in dem anderen Pointer-Referenzen Thread...


----------



## byte (12. Feb 2009)

Spacerat hat gesagt.:
			
		

> In dem Overhead einer Java-Methode muss z.B. noch stehen, ob diese "private", "protected" oder wie auch immer ist, welche Parameter zur Ausführung nötig sind usw (Methoden-Signatur).In "vtables" liegen ausschliesslich Adressen. Will sagen, in einer Ausfürbaren Datei aus C++ entfallen diese Abfragen, weil sie vom Kompiler oder Linker bereits erkannt und eliminiert bzw. optimiert wurden. Deswegen würde ich diese "vtables" nicht als Overhead im Sinne von Java-Overheads bezeichnen.


Du sprichst die ganze Zeit von Java-Overhead, ohne jemals zu definieren, was Du damit meinst. In Fall der Sichtbarkeiten liegst Du schon mal daneben, die interessieren auch in Java nur den Compiler.


----------



## Ebenius (12. Feb 2009)

byto hat gesagt.:
			
		

> In Fall der Sichtbarkeiten liegst Du schon mal daneben, die interessieren auch in Java nur den Compiler.


Heieiei jetzt wird's haarig. Sichtbarkeiten interessieren in Java auch die Reflection-API, somit müssen sie zur Laufzeit verfügbar sein. Natürlich gebe ich Spacerat in sofern recht, als dass der Overhead ─ ich denke damit meint er pauschal alle nicht die Nutzdaten betreffenden Daten eines Objektes ─ in der Regel größer ist, als in einem mit C++ kompilierten Programm. Alles andere ist von Seiten Spacerat's aus jetzt Wortklauberei die daher rührt, dass er eine Aussage verteidigen muss die er sich nicht richtig überlegt hatte.

Ebenius


----------



## byte (12. Feb 2009)

Ebenius hat gesagt.:
			
		

> byto hat gesagt.:
> 
> 
> 
> ...


Die Informationen sind zur Laufzeit verfügbar, gehören aber zu den statischen Informationen einer Klasse, die der Classloader einmalig lädt, wenn die Klasse zum ersten Mal benutzt wird. Den kompilierten Code interessieren die Sichtbarkeiten aber nicht mehr, weil diese schon vom Compiler geprüft wurden.
Anders siehts natürlich aus, wenn man per Reflection API den Aufruf macht. Aber Reflection ist ja was grundlegend anderes und hier nicht Thema.


----------



## Ebenius (12. Feb 2009)

byto hat gesagt.:
			
		

> Die Informationen sind zur Laufzeit verfügbar, gehören aber zu den statischen Informationen einer Klasse, die der Classloader einmalig lädt, wenn die Klasse zum ersten Mal benutzt wird. Den kompilierten Code interessieren die Sichtbarkeiten aber nicht mehr, weil diese schon vom Compiler geprüft wurden.
> Anders siehts natürlich aus, wenn man per Reflection API den Aufruf macht.


Du hast recht. Es ging allerdings nur um Overhead im Speicher. Ich hab die Reflection-API einfach als ad-hoc-Beleg angeführt, dass die Informationen im Speicher vorhanden sein müssen.

Ebenius


----------



## byte (12. Feb 2009)

Und ich dachte, es geht um Performance-Overhead. Aber im Grunde genommen wurde der Begriff "Overhead" nur so in den Raum geworfen ohne jemals zu definieren, was damit gemeint ist. :roll:

Speicher-Overhead ist natürlich da, schon alleine durch die VM. Aber der Overhead bringt ja auch Vorteile. Dank Reflection API sind z.B. dynamische Proxies möglich, die wohl kaum mehr wegzudenken sind aus modernen Frameworks. Insofern kann man das nicht perse als Nachteil abstempeln.


----------



## Ebenius (12. Feb 2009)

byto, da musst Du mal viel weiter hochblättern; Spacerat hatte eben angefangen mit Overhead in Zusammenhang mit dem sizeof-Konstrukt aus C++.


----------



## byte (12. Feb 2009)

Er hat aber auch von Sprungadressen berichtet, was wieder für Performance sprechen würde. 

Is ja auch wurscht. Die Diskussion ist eh Käse.


----------



## Ebenius (12. Feb 2009)

byto hat gesagt.:
			
		

> Er hat aber auch von Sprungadressen berichtet, was wieder für Performance sprechen würde.


Ging auch dort nur um den Speicher-Overhead wegen der VMT. Käsediskussion beendet.


----------



## Spacerat (12. Feb 2009)

Handbuch der Javaprogrammierung 5. Auflage Guido Krüger Kap. 50.1 Performancetuning Einleitung hat gesagt.:
			
		

> Leider ist auch ein Just-In-Time-Compiler kein Allheilmittel gegen Performanceprobleme. Zwar ist er in der Lage, bestimmte Codeteile so stark zu beschleunigen, dass ihre Ablaufgeschwindigkeit der von kompiliertem C-Code nahekommt. Andererseits gibt es nach wie vor genügend Möglichkeiten, Programme zu schreiben, die inhärent langsamen Code enthalten, der auch von einem Just-In-Time-Compiler nicht entscheidend verbessert werden kann. Zudem ensteht durch den Einsatz des JIT ein gewisser Overhead, der möglicherweise einen Netto-Performancegewinn verhindert, denn das Kompilieren des Bytecodes kostet Zeit und zusätzlichen Speicher.


Von jenem "gewissen Overhead" ist die Rede. Dieser nicht zu unterschätzende Overhead der nunmal entsteht, wenn JIT zur Laufzeit z.B. eine neue Klasse laden muss wobei ihm dann auch erst z.B. die Sichtbarkeit der aufzurufenden Methode auffallen kann. Eben all, die Informationen, die in bei C++ z.B. schon beim Kompilieren oder Linken auffallen. C++ Kompilierter Code muss zur Ausführbarkeit ausschliesslich DLLs nachladen (und das passiert auch nur einmal beim Programmstart), während der JIT sich mit dem Laden von benötigten Klassen auch noch zur Laufzeit beschäftigen muss. Was solls... Ich red' Schwachfug. Blame me...
BTW.: Schwachfug wäre es zu behaupten, Java hätte dank JIT alle merkmale einer Interpretativen Sprache abgelegt.


----------



## maki (12. Feb 2009)

>> Was kann Java? Wofür benutzt man es?

Man kann Java benutzen (eine Prise C++ kann helfen) um eigentlich hochintelligente Menschen miteinander streiten zu lassen *g*


----------



## Landei (12. Feb 2009)

>> Was kann Java? Wofür benutzt man es? 

Man kann Java benutzen, um zu zeigen, was aus einer guten Idee werden kann, wenn man sie nicht dauernd den aktuellen Erfordernissen anpaßt.


----------



## Ebenius (12. Feb 2009)

Landei hat gesagt.:
			
		

> >> Was kann Java? Wofür benutzt man es?
> 
> Man kann Java benutzen, um zu zeigen, was aus einer guten Idee werden kann, wenn man sie nicht dauernd den aktuellen Erfordernissen anpaßt.


Eine stabile Sprache mit guten Frameworks und exzellenten Tools.

Sagt Ebenius, ...
... der sich immer sehr freut wenn Programmiersprachen sich eben nicht dauernd anpassen.


----------



## Landei (12. Feb 2009)

Ersetzte "stabil" durch "starr" und "gut" (bzw. "exzellent") durch "annehmbar", dann kommen wir unter einen Hut :-D

Ein bißchen mehr Bewegung täte Java wirklich gut. Ist ja nicht so, dass es keine guten Vorbilder gäbe. Und viele interessante Sachen lassen sich realisieren ohne die Kompatibilität zu beeinträchtigen.


----------



## Ebenius (12. Feb 2009)

Ich will doch gar nicht unter einen Hut :shock:

Und starr? JLS 3 ist noch nicht sehr alt. Und die Neuerungen in JLS 3 so lange zu diskutieren wie geschehen, kann ich gut verstehen.

Ebenius


----------



## Landei (12. Feb 2009)

Wie lange gibt es Nice, Groovy und Scala? Wie lange hat C# schon die Nase vorn?

Sicher, niemand will ein Featuritis-Monster, aber dieses Schneckentempo ist einfach nicht auszuhalten. Wenn die Entwicklung der Programmiersprachen mit dem Wahnsinns-Speed erfolgt wäre, wäre COBOL immer noch "State of the Art"


----------



## Ebenius (12. Feb 2009)

Dann hätte man sich so einige Krankheiten auch sparen können. Und ob C# die Nase vorn hat? Ich fand die Sprache nie besser und, ja, ich hab sie benutzen müssen. Aber das ist ohnehin Geschmackssache.

Remis?


----------



## Leroy42 (12. Feb 2009)

Ebenius hat gesagt.:
			
		

> Remis?



Meiner Meinung nach: Ja!

Ich denke, diese _Diskussion_ dauert schon viel zu lange....


----------



## xonic (15. Feb 2009)

Ein super in Java geschriebenes Image Upload Tool http://www.abload.de/tool.php


----------

