【问题标题】:AS3 Custom Object to ByteArray then to Custom ObjectAS3 自定义对象到 ByteArray,然后到自定义对象
【发布时间】:2011-04-14 01:20:13
【问题描述】:

在读取自定义对象的字节数组时遇到问题。任何帮助表示赞赏

public class CustomObject extends Object {
public function CustomObject() {
public var _x:Number =  100
public var _y:Number = 10
public var _z:Number  = 60
}
}

var cObj:CustomObject = new CustomObject()
var bytes:ByteArray = new ByteArray()
bytes.writeObject(cObj)
bytes.compress()

//read
try { bytes.uncompress() } catch (e:Error) { }
var obj:CustomObject = bytes.readObject() as CustomObject

trace(obj) // null why?!
trace(obj._z) // Obviously - TypeError: Error #1009: Cannot access a property or method of a null object reference. 

【问题讨论】:

    标签: actionscript-3 object bytearray


    【解决方案1】:

    查看ByteArray.readObject() 返回的对象。您可能会看到所有属性都在那里,但类型信息丢失了。所以,你可以通过创建一些来解决这个问题

    public static function fromObject(value:Object):CustomObject {
        var result:CustomObject = new CustomObject();
        result._x = value._x;
        //and so on...
        return result;
    }
    

    【讨论】:

    • 问题是自定义对象中有另一个自定义对象...例如 cObj._myHome = myHome,其中 myHome:MyHome 扩展对象
    【解决方案2】:

    你的 CustomObject 类是错误的,它实际上应该抛出一个错误,应该是这个

    公共类 CustomObject { 公共变量_x:数字= 100 公共变量_y:数字= 10 公共变量_z:数字= 60 公共函数自定义对象() { } }

    编辑:

    听起来 macke 有道理,因为这行得通...

    //读 尝试 { bytes.uncompress() } catch (e:Error) { } var obj:Object = bytes.readObject(); trace(obj) // [对象对象] 跟踪(obj._z)// 60

    【讨论】:

    • 我认为在这种情况下这并不重要吗?
    • 实际上我不确定,需要对其进行测试......但 CustomObject 类是一个更大的问题!
    • 真棒 var obj:Object = bytes.readObject();和 registerClassAlias("com.example.eg", ExampleClass);诀窍
    • 关于问题中的 CustomObject theres 语法错误,但在实际类中它被正确编码..
    【解决方案3】:

    您要做的是使用 registerClassAlias 方法将类型信息与数据一起注册。这样,Flash 将知道如何序列化/反序列化您的对象。这是来自 Adob​​e 的 documentation 的一些示例代码:

    registerClassAlias("com.example.eg", ExampleClass);
    var eg1:ExampleClass = new ExampleClass();
    var ba:ByteArray = new ByteArray();
    ba.writeObject(eg1);
    ba.position = 0;
    var eg2:* = ba.readObject();
    trace(eg2 is ExampleClass); // true
    

    需要注意的是,所有需要序列化的类型必须注册才能保存类型信息。因此,如果您的类型引用了另一种类型,则也必须注册它。

    【讨论】:

    • 哇注册类,听起来很贵..这会导致任何性能问题还是什么,啊,我会谷歌它
    • 并非如此。它确实在数据中存储了有关类型的信息,但它的效率并不算太低。它并没有真正影响处理。它用于在Flash平台中广泛用于数据传输的AMF协议中存储对象。除了手动存储类型信息和提供从原始对象数据到特定类型的手动转换之外,这是您唯一的选择,而且还不错。
    • 是的,我使用“自定义”对象,因此它比 new Object();所以想知道它是否会在奇怪的 as3 中导致性能问题
    • 除非您有巨大的对象图或一致地序列化/反序列化大量对象,否则我不会担心。在任何一种情况下,添加输入信息可能是您最不麻烦的事情。
    【解决方案4】:

    要将自定义类序列化为ByteArray,必须将registerClassAlias放入调用byteArray.writeObject()函数的类的构造函数中。

    如果您不这样做,您的自定义类将被序列化为 Object 类型。我在下面的序列化函数中调用了registerClassAlias,并且我的自定义类一直被序列化为Object,直到我将registerClassAlias 移到构造函数中。

    public class MyClass{
        public function MyClass(){
            registerClassAlias("com.myclass", MyClass); // Ok, serializes as MyClass
            serialize( new MyClass() );
        }
    
        private function serialize( _c:MyClass ){
            var byteArray:ByteArray = new ByteArray();
            byteArray.writeObject( _c );
            //registerClassAlias("com.myclass", MyClass); Not ok, serialized as Object
            EncryptedLocalStorage.setItem('key', byteArray);
        }
    }
    

    【讨论】:

    • 对 registerClassAlias 的调用必须在对 ByteArray:writeObject 的调用之前,但它不必必须在要序列化的类的构造函数中。
    猜你喜欢
    • 2012-10-10
    • 2023-04-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多