Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Dart TypedData and big/little endian representation

If I run the following code:

Uint8List bytes = Uint8List.fromList([1, 0, 0, 128]);
ByteBuffer byteBuffer = bytes.buffer;
Uint16List sixteenBitList = byteBuffer.asUint16List();
print(sixteenBitList);

I get the following result:

[1, 32768]

Since the original values were

00000001 00000000 00000000 10000000
1        0        0        128

I would have expected them to be combined like this:

0000000100000000 0000000010000000
256              128

Instead, I got this:

0000000000000001 1000000000000000
1                32768

That's little endian, right? I'm running this code on my Mac. Is the reason I got the result above because my Mac uses little endian? If I ran the same code on a big endian computer, would it give a different result? (I get the same result on DartPad, but I don't know what machine DartPad is running on.)

like image 354
Suragch Avatar asked Mar 02 '23 20:03

Suragch


2 Answers

Yes it would be expected to give a different result. You would get your expected result on a big endian system. Your current method of viewing your byte data uses the endianness of the host system. This includes DartPad since the code running in DartPad is being compiled to JS, which is still running on that same little endian system.

There is no set endianness for the Dart language. However, some methods of viewing byte data do explicitly set an endianness like the ByteData class.

like image 105
Christopher Moore Avatar answered Apr 01 '23 06:04

Christopher Moore


Here is some additional information to Christopher Moore's answer.

You can check the endianness of your computer with the following:

print(Endian.host == Endian.little);

Most personal computers use little endian architecture so that will usually return true.

You can specify the endianness with which you want to view the data by using ByteData instead of BytesBuffer:

import 'dart:typed_data';

void main() {
  Uint8List byteList = Uint8List.fromList([1, 0, 0, 128]);
  ByteData byteData = ByteData.sublistView(byteList);

  int value = byteData.getUint16(0, Endian.big);
  print(value.toRadixString(2).padLeft(16, '0'));
  
  value = byteData.getUint16(2, Endian.big);
  print(value.toRadixString(2).padLeft(16, '0'));
}

The result is:

0000000100000000 0000000010000000

If you change Endian.big to Endian.little the result will be:

0000000000000001 1000000000000000

You can read more about this here:

  • Working with bytes in Dart
like image 31
Suragch Avatar answered Apr 01 '23 07:04

Suragch