如果我将数组和矢量的精确类似地序列化为ByteArrays,我的矢量大小几乎是两倍。检查此代码:
var arr:Array = [];
var vec:Vector.<int> = new Vector.<int>;
for (var i:int = 0; i < 100; ++i) {
arr.push(i);
vec.push(i);
}
var b:ByteArray;
b = new ByteArray();
b.writeObject(arr);
trace("arr",b.length); // arr 204
b = new ByteArray();
b.writeObject(vec);
trace("vec",b.length); // vec 404
似乎代表了Adobe的错误或未经优化的实施......?或者我在这里遗漏了什么?
答案 0 :(得分:2)
根据AMF 3 specification AMF将数组存储为单独的,针对密集数组方式进行优化,并以优化的方式存储整数,以最小化用于小整数的字节数。这样,值为0-99的数组将存储为:
00000000 0x09 ; array marker
00000001 0x81 0x49 ; array length in U29A format = 100
00000003 0x01 ; UTF8-empty - this array is all dense
00000004 to 000000CB - integer data, first integer marker 0x04, then an integer in U29.
所有整数都小于128,因此它们表示为等于整数的单字节。这使得数组中的小 int占用2个字节而不是满4个甚至8个大整数。
现在,对于Vector,由于Vector默认为密集,因此最好不要将整数转换为U29格式,因为大于0x40000000的任何内容都会转换为DOUBLE(又名Number
),这是对于向量不好,所以Vector.<int>
按原样存储,向量内每个整数4个字节。
00000000 0x0D ; vector-int marker
00000001 0x81 0x49 ; U29 length of the vector = 100
00000003 0x00 ; fixed vector marker, 0 is not fixed
00000004 to 00000193 - integers in U32
因此,对于小整数,一个数组比一个向量的int占用更少的空间,但是对于大整数,每个存储的数组最多可以占用9个字节,而Vector总是使用4个字节每整数。
请考虑对您的代码进行以下更改:
var arr:Array = [];
var vec:Vector.<int> = new Vector.<int>;
for (var i:int = 0; i < 100; ++i) {
var x:int=Math.floor(Math.random()*4294967295); // 0 to 0xFFFFFFFE
arr.push(x);
vec.push(x);
trace(x);
}
var b:ByteArray;
b = new ByteArray();
b.writeObject(arr);
trace("arr",b.length); // some variable value will be shown, up to 724
b = new ByteArray();
b.writeObject(vec);
trace("vec",b.length); // here the value will always be 404