# For-Schleifen - byte statt int?



## Meldanor (27. Okt 2009)

Hi Leute,

der primitive Datentyp byte kann Zahlen von -2^7 bis 2^7 -1 speichern, int ja -2^31 bis 2^31 -1, da byte 8 bit zur verfügung hat und int 32.
AUch wenn diese Frage absolut minimalistisch ist:

Ist es speichereffizienter in einer for schleife statt dem üblichen int *byte*zu verwenden?

Ich spreche hier von for schleifen, wo ich die Anzahl der schleifen exakt weiß wie


```
for(int i = 0 ; i < 10 ; ++i)
```

und nicht von schleifen, wo *i* eine beliebige größe haben kann wie


```
for(int i = 0 ; i < liste.length ; ++i)
```

Natürlich gehe ich auch davon aus, dass *i* niemals einen Wert von > byte erreichen kann(oder short , je nachdem).

Eine Anschlussfrage ist, ob es sich lohnt, wenn *i* in der Schleife benutzt wird und zum Beispiel ein Methode n-mal aufgerufen wird mit einem Paramater int wie z.B. bei PreparedStatements.
Bsp:

```
for(byte i = 0 ; i < 3 ; ++i){
    updateAllMaxMemberStatement.setString(i+1, data[i]);
    deletePupilFromAllStandsStatement.setString(i+1, data[i]);
    deleteSinglePupilStatement.setString(i+1, data[i]);

}
```
Es wird ja dann *i*, was ein byte ist, nach int gecasted, oder? Gehen wir davon aus, dass byte statt int wirklich speicher-effizienter ist, so stellt sich hier die Frage:
Ist die Effizenz des Speicherns nichtig, da eine Cast dies aufhebt(keine Ahnung, ob ein Cast mehr Speicher verbraucht als ein Zahl, die schon immer ein Int war oder ob dieser Vorgang Rechenleistung verbraucht).

Bitte vergesst nicht, ich weiß, dass ich mich hier um bits und bytes streite, mich interessiert nur, ob dies ein korrekter Gedankengang ist oder aber ich falsch liege auf Grund von Java Internen Mechanismen.

Mfg
mel


----------



## tfa (27. Okt 2009)

Der Speicherverbrauch eines Bytes hängt von der jeweiligen Implementierung der JVM ab. Normalerweise ist es effizienter, wenn Daten bzw. Objekte "aligned" im Speicher liegen. Also kann es durchaus sein, dass ein byte tatsächlich 32 oder gar 64 Bit beansprucht. Jedenfalls ist der Unterschied im Verbrauch so gering, dass unnötig ist, sich darüber den Kopf zu zerbrechen. 
(Bei großen byte-Arrays sollten allerdings schon gepackt im Speicher liegen.)


----------



## Marco13 (27. Okt 2009)

Bei Variablen ist es egal: Jedes byte, short oder char wird innerhalb der JVM automatisch als ein int (32 bit) verrechnet.


----------



## tfa (27. Okt 2009)

Marco13 hat gesagt.:


> Bei Variablen ist es egal: Jedes byte, short oder char wird innerhalb der JVM automatisch als ein int (32 bit) verrechnet.


Nicht unbedingt.
Size of a byte in memory - Java - Stack Overflow


----------



## Marco13 (27. Okt 2009)

Mit der (zugegeben vielleicht etwas unpräzisen) Formulierung "Bei Variablen..." meinte ich, dass bei sowas wie
byte a = 1;
byte b = 2;
byte c = a+b;
in der letzten Zeile innerhalb der VM tatsächlich zwei 32bit-Werte addiert werden. Dass die Daten als Array unterscheidlich viel Speicher belegen ist ja klar


----------



## tfa (27. Okt 2009)

Ich nahm an, es ging dem TS um den Speicherplatz der byte-Variablen (in dem Test aus dem Link stehen auch nur Variablen, keine Arrays).


----------



## Meldanor (27. Okt 2009)

Ja, da es mir hier primär um die temporären Variablen in einer Vorschleife geht.
Danke für die bisherigen Antworten.
Also ist es vorallem von der JVM abhängig?


----------



## tfa (27. Okt 2009)

Ja, aber wie gesagt, es ist völlig unerheblich, ob da nun 1 oder 4 oder 8 Bytes verwendet werden. Hauptsache dein Programm funktioniert. Speicher ist billig. Oder schreibst du Java-Programme für Smart-Cards?


----------



## Meldanor (27. Okt 2009)

Nee...speicher hab ich hier genug und das ist auhc nicht das Problem.
Ich sagte ja bereits, dass ich mir bewusst bin, dass ich über Bits und Bytes diskutiere. Es war eher eine ... theoretische Sache als eine praktische.
Mir fiel jedoch in dem Zusammenhang noch eine Frage ein:
Wenn, wie du sagtest, die JVM automatisch das regelt, wozu existieren dann byte,short etc. überhaupt, wenn sie weniger speichern können,aber genau soviel Speicher wie ein int verbrauchen?


----------



## musiKk (27. Okt 2009)

"Theoretische Sache" klingt meist wie premature Optimization. Sowas kann von Fall zu Fall unterschiedlich sein.

Dass es short überhaupt gibt, habe ich bis vor kurzem gar nicht mehr richtig vor Augen gehabt. Ich kann mich gar nicht erinnern, das je in fremdem Code gesehen zu haben und verwende es selbst auch nicht. Byte nehme ich für I/O. Und sonst gibts ja nur noch int und long und da gibt es auch einen tatsächlichen Unterschied im Speicherverbrauch.


----------



## Ark (27. Okt 2009)

Die unterschiedlichen Datentypen verbrauchen schon unterschiedlich viel Speicher, sonst würde es sie ja gar nicht geben.

Zumindest solange sie nur im Arbeitsspeicher rumlungern, verbrauchen sie zunächst(!) genau den durch den Datentyp bestimmten Speicherplatz. Wenn sie jedoch in Register geladen werden, um Berechnungen durchzuführen, so kann davon ausgegangen werden, dass sie die ganze Breite des Registers beanspruchen, vor allem, wenn sie zusammen mit int verarbeitet werden.

Wie wirkt sich das aus? Stellen wir uns vor, unser Prozessor arbeitet mit 32 Bit breiten Registern. Wenn wir ein int laden, können wir dessen Wert direkt mit einem Befehl ins Register schieben. Wenn wir jedoch nur ein byte laden, dann gibt es zwei Möglichkeiten:


Im Arbeitsspeicher wird der obere Bereich, der durch das byte eigentlich nicht belegt wird, auf 0 gesetzt bzw. mit Nullen aufgefüllt, damit beim Zugriff direkt die oberen Bits richtig gesetzt sind. So kann die Zahl in den Prozessor geladen werden, als handle es sich um ein int. Nachteil: Wir brauchen mehr Speicher. Das nennt sich dann Alignment. (Entsprechendes gilt bei negativem Vorzeichen.)
Der verbrauchte Platz im Arbeitsspeicher bleibt bei dem einen Byte, den ein byte nun mal belegt. Dadurch spart man Arbeitsspeicher, aber nachdem das byte in die unteren 8 Bits des Registers geladen wurden, müssen nachträglich die oberen Bits im Register je nach Vorzeichen gesetzt oder gelöscht werden, wenn die Operation mit einem weiteren Operanden größeren Datentyps (z.B. int) durchgeführt wird. Dieser Vorgang kostet Zeit.
Nachdem in irgendeiner Spezifikation (glaube ich jedenfalls) steht, dass alle 32-Bit-Operationen einer JVM in einem Zug abgearbeitet werden müssen, sollte es nicht verwunderlich sein, dass int der schnellste Datentyp ist. (Möglicherweise werfe ich hier auch gerade Dinge in einen Topf, die nichts miteinander zu tun haben. ^^) long benötigt mehr Zeit, zumindest auf 32-Bit-Maschinen, da hier die Operationen in mehreren Zügen durchgeführt werden müssen.

Ark


----------



## Marco13 (27. Okt 2009)

Meldanor hat gesagt.:


> wozu existieren dann byte,short etc. überhaupt, wenn sie weniger speichern können,aber genau soviel Speicher wie ein int verbrauchen?



In arrays benötigen sie eben weniger Speicher. Aber sobald mit den einzelnen Werten _gerechnet_ wird, werden sie alle als int behandelt.


----------

