Androidcoder
Androidcoder

Reputation: 4679

Is Byte implemented as Int anyway?

I had a java game book recommend implementing all data as Int when possible, that that type runs the fastest. It said the Byte, Char, and Boolean are implemented as Int anyway, so you don't save space and the casting you end up having to do in the code because of the Byte data will slow it down. For instance, a cast is needed for

a = (byte)(b+c);

since the addition result is an Int, even when a,b, and c are all declared as Bytes.

I currently have a huge 2D array declared as Byte for my game, to save space and for bitwise operations. Is it actually saving space? I've also seen bitwise operations done on Ints in examples, do bitwise operations work as expected on Ints?

Upvotes: 4

Views: 252

Answers (4)

Michał Kosmulski
Michał Kosmulski

Reputation: 10020

The answer depends on whether you are working with a single variable of type byte or with a byte array, byte[]. A byte array does indeed save space, with each Java byte using just a byte of memory (plus a constant amount of housekeeping data for the array object). However, a single local variable of type byte is actually stored as an int on the stack and takes the corresponding 4 bytes of memory. This is even expressed in the bytecode - there is the opcode baload - "Load byte or boolean from array" but there is no opcode for loading a byte from local variable like there is iload for ints. Similarily, local char and boolean variables actually are stored on the stack as an int and int-based opcodes are used to access them.

The entry 2.6.1 in JLS also says that all local variables take either one or two "slots" on the stack, so the single-slot types byte, char, float and int all take the same space. The JVM cannot address a unit smaller than a single such slot, so in the case of a byte, 3 bytes are so to say wasted.

To wrap it up: do use byte arrays to save space, but in the case of individual variables, using a byte instead of int won't save space and may even have a small negative performance impact (it may however be required if you need byte for the semantics, e.g. counter wrapping behavior and such).

Upvotes: 1

arshajii
arshajii

Reputation: 129587

This is generally incorrect. In fact, this is outlined in the JVM Specification §2.3:

The primitive data types supported by the Java Virtual Machine are the numeric types, the boolean type (§2.3.4), and the returnAddress type (§2.3.3).

The numeric types consist of the integral types (§2.3.1) and the floating-point types (§2.3.2).

The integral types are:

  • byte, whose values are 8-bit signed two's-complement integers, and whose default value is zero

  • short, whose values are 16-bit signed two's-complement integers, and whose default value is zero

  • int, whose values are 32-bit signed two's-complement integers, and whose default value is zero

  • long, whose values are 64-bit signed two's-complement integers, and whose default value is zero

  • char, whose values are 16-bit unsigned integers representing Unicode code points in the Basic Multilingual Plane, encoded with UTF-16, and whose default value is the null code point ('\u0000')

Now, for boolean it's slightly a different story. From §2.3.4:

Although the Java Virtual Machine defines a boolean type, it only provides very limited support for it. There are no Java Virtual Machine instructions solely dedicated to operations on boolean values. Instead, expressions in the Java programming language that operate on boolean values are compiled to use values of the Java Virtual Machine int data type.

You can see differences in the bytecode depending on whether you use a byte[] or an int[], so they're not identical:

byte[] b = {42};
ICONST_1
NEWARRAY T_BYTE
DUP
ICONST_0
BIPUSH 42
BASTORE
ASTORE 1

vs

int[] b = {42};
ICONST_1
NEWARRAY T_INT
DUP
ICONST_0
BIPUSH 42
IASTORE
ASTORE 1

Is it actually saving space?

Yes, it likely is, especially if the array is very large.

do bitwise operations work as expected on Ints?

Yes, they do.

Upvotes: 6

Waman
Waman

Reputation: 1179

Yes, when you perform a byte addition the return value is always an integer, reason being that 8bit + 8bit addition can always result in a value which is greater than 8bit.

e.g.

decimal | binary

255 |   1111 1111
121 |   0111 1001

376 | 1 0111 1000

So if you try to store it in a byte again will definitely result in loss of data. Instead of 376 you would get "120" if typecasting to byte is done.

You can definitely use int instead of byte and also the bit wise operations work perfectly on int. refer: http://www.tutorialspoint.com/java/java_bitwise_operators_examples.htm

Upvotes: 0

tckmn
tckmn

Reputation: 59343

It is true that byte + byte = int, requiring a cast, but bytes are implemented with 8 bits of data in memory, while ints are 32 bits. Therefore, using bytes will decrease the amount of memory that an array takes up by 4 times.

For example, if you had a 10 by 10 array of bytes, its size would be 800, but a 10 by 10 array of ints' size would be 3200.

More information on this

Upvotes: 1

Related Questions