2

Ebean ORM を使用して、MySQL データベースで Java クラスをシリアライズしたいと考えています。

私のクラス定義は次のようになります。

public class Test implements Serializable
{
    @Id
    private Long id;
    ...
    ...
    ...
    @Lob
    private MyClass1 obj1;
    @Lob
    private MyClass2 obj2;
    ...
    ...
    //getters and setters
}

私のクラス MyClass1 と MyClass2 は基本的に

float[] 

Hashmap<String, Float> 

どちらもシリアライズ可能なインターフェースを実装しています。

次のものを使用してクラスを作成する必要はありません。

@Lob
byte[] obj1bytes;
@Transient
MyClass1 obj1Obj;
@Lob
byte[] obj2bytes;
@Transient
MyClass2 obj2Obj;
//getters and setters

私が取得したいのは、byte[] 配列を使用して Test クラスの obj1 と obj2 を保持する必要なく、このクラスを自動的にシリアライズおよびデシリアライズすることです。

Ebean.save(testClassInstance);
Ebean.find(Test.class, ID);

EDIT1: MyClass1 は次のように定義されています。

public class MyClass1 implements Interface1 {
    private float[] vector;
    public MyClass1 () {
    }
    public MyClass1 (float[] vector) {
        this.vector = vector;
    }
    public float[] getVector() {
        return vector;
    }
    public void setVector(float[] vector) {
       this.vector = vector;
    }
    @Override
    public byte[] serialize() throws Exception {
        ByteArrayOutputStream byteOut = new ByteArrayOutputStream();
        ObjectOutputStream out = new ObjectOutputStream(byteOut);
        out.writeObject(object);
        out.close();            
        return byteOut.toByteArray();
    }
    @Override
    public void deserialize(byte[] bytes) throws Exception {
        ByteArrayInputStream byteInt = new ByteArrayInputStream(bytes);
        ObjectInputStream out = new ObjectInputStream(byteInt);
        vector = (float[])out.readObject();
    }
    @Override
    public float cossim(MyClass1 v) throws Exception {
        method logic
    }
    @Override
    public MyClass1 add(MyClass1 v) throws Exception {
        method logic
   }
}

MyClass2 は MyClass1 として定義されていますが、float[] ベクトルの代わりに HashMap < String, Float > () があるだけです。注目に値する唯一の違いは、serialize() と deserialize() です。

@Override
public byte[] serialize() throws Exception {
    ByteArrayOutputStream outStream = new ByteArrayOutputStream();
    DataOutputStream out = new DataOutputStream(outStream);
    out.writeInt(map.size());
    Iterator<String> iterator = map.keySet().iterator();
    while (iterator.hasNext()) {
        String key = iterator.next();
        out.writeUTF(key);
        out.writeFloat(map.get(key));
    }
    return outStream.toByteArray();
}

@Override
public void deserialize(byte[] bytes) throws Exception {
    try {
      ByteArrayInputStream inStream = new ByteArrayInputStream(bytes);
      DataInputStream in = new DataInputStream(inStream);
      this.map = new HashMap<>();
      int n = in.readInt();
      for (int i = 0; i < n; i++) {
        map.put(in.readUTF(), in.readFloat());
      }
    } catch (Exception ex) {
      throw ex;
    }
}
4

2 に答える 2

0

実際にはラップする必要はなくfloat[]HashMap<String,float>それら自体がシリアライズ可能です。

もう 1 つのことは、使用できるよりもシリアライズ可能でMyClass1ある場合です。このウィキブックによると、MyClass2@Lob

JPA のデフォルトでは、リレーションシップまたは基本型 (文字列、数値、時間、プリミティブ) ではないシリアライズ可能な属性は、BLOB フィールドにシリアライズされます。

@Lobそのウィキブックには、 forを使用した例もありImageます。

@Entity
public class Employee {
    ...
    @Basic(fetch=FetchType.LAZY)
    @Lob
    private Image picture;
    ...
}

これがお役に立てば幸いです。

于 2013-07-26T16:57:02.563 に答える
0

返信後、コーディングを行いました。

条件: ClassB のフィールドはシリアライズ可能であり、フィールドのフィールドはシリアライズ可能である必要があります。

クラスB:

import java.io.Serializable;

public class ClassB implements Serializable{
    private static final long serialVersionUID = 1L;
    String b;

    public String getB() {
        return b;
    }

    public void setB(String b) {
        this.b = b;
    }

}

クラスA:

import java.io.Serializable;

import javax.persistence.Entity;
import javax.persistence.Id;
import javax.persistence.Lob;

@Entity
public class ClassA implements Serializable{
    private static final long serialVersionUID = 1L;
    @Id
    String a;
    @Lob
    ClassB b;

    public String getA() {
        return a;
    }
    public void setA(String a) {
        this.a = a;
    }
    public ClassB getB() {
        return b;
    }
    public void setB(ClassB b) {
        this.b = b;
    }

}

ここで、ClassA には ClassB オブジェクトが含まれます。ClassB に任意のロジックを追加でき、機能します。シリアライズとデシリアライズのオーバーライドに小さな問題があります。そうする必要はないと思います。シリアル化されているため、デフォルトで実行されます。そして最後に、これらのコードは私が試したとおりに機能します。

これがあなたを助けることを願っています。

于 2013-07-29T06:19:26.670 に答える