AS3: Может ли ByteArray вернуть свое содержимое в виде строки с двумя байтами на символ Юникода?

var bytes:ByteArray = new ByteArray;
bytes.writeInt(0);

trace(bytes.length); // prints 4
trace(bytes.toString().length); // prints 4

Когда я запускаю приведенный выше код, вывод предполагает, что каждый символ в строке, возвращаемой toString, содержит один байт из ByteArray. Это, конечно, хорошо, если вы хотите отобразить содержимое ByteArray, но не так здорово, если вы хотите отправить его содержимое, закодированное в виде строки, а размер строки имеет значение.

Можно ли получить строку из ByteArray, где каждый символ в строке содержит два байта из ByteArray?


person Anders    schedule 13.08.2010    source источник


Ответы (2)


Вы можете переосмыслить свой ByteArray как содержащий только шорты. Это позволяет читать два байта за раз и получать одно числовое значение, представляющее их оба. Затем вы можете взять эти числа и интерпретировать их как коды символов. Наконец, создайте String из этих кодов символов, и все готово.

public static function encode(ba:ByteArray):String {
    var origPos:uint = ba.position;
    var result:Array = new Array();

    for (ba.position = 0; ba.position < ba.length - 1; )
        result.push(ba.readShort());

    if (ba.position != ba.length)
        result.push(ba.readByte() << 8);

    ba.position = origPos;
    return String.fromCharCode.apply(null, result);
}

Следует обратить внимание на одно особое обстоятельство. Если вы попытаетесь прочитать шорт из ByteArray, когда в нем остался только один байт, будет выдано исключение. В этом случае вы должны вместо этого вызвать readByte со значением, сдвинутым на 8 бит. Это то же самое, как если бы исходный ByteArray имел в конце дополнительный 0 байт. (выравнивая длину)

Теперь, что касается декодирования этой строки... Получите код каждого символа и поместите их в новый ByteArray как шорты. Он будет идентичен оригиналу, за исключением случаев, когда оригинал имеет нечетное количество байтов, и в этом случае декодированный ByteArray будет иметь дополнительный 0 байт в конце.

public static function decode(str:String):ByteArray {
    var result:ByteArray = new ByteArray();
    for (var i:int = 0; i < str.length; ++i) {
        result.writeShort(str.charCodeAt(i));
    }
    result.position = 0;
    return result;
}

В действии:

var ba:ByteArray = new ByteArray();

ba.writeInt(47);
ba.writeUTF("Goodbye, cruel world!");

var str:String = encode(ba);
ba = decode(str);

trace(ba.readInt());
trace(ba.readUTF());
person Gunslinger47    schedule 14.08.2010

Ваш вопрос немного сбивает с толку. Вы записали 4-байтовый int в свой ByteArray. Вы не написали в него никаких символов (юникода или других). Если вы хотите передать текст, напишите текст и передайте его как UTF8. Это займет меньше места, чем два байта для каждого символа, по крайней мере, для большинства западных языков.

Но, честно говоря, я не уверен, что понял, чего вы пытаетесь достичь. Вы хотите отправить числа или текст? С каким бэкэндом вы разговариваете? Вам вообще нужен ByteArray?

person Juan Pablo Califano    schedule 13.08.2010