Tôi thường tránh cho lớp biết cách tự xê-ri hóa, vì một vài lý do. Đầu tiên, nếu bạn muốn (de) tuần tự hóa sang / từ một định dạng khác, bây giờ bạn cần làm ô nhiễm mô hình với logic bổ sung đó. Nếu mô hình được truy cập thông qua một giao diện, thì bạn cũng làm ô nhiễm hợp đồng.
public class Image
{
public void toJPG(String filePath) { ... }
public Image fromJPG(String filePath) { ... }
}
Nhưng nếu bạn muốn tuần tự hóa nó thành / từ PNG và GIF thì sao? Bây giờ lớp học trở thành
public class Image
{
public void toJPG(String filePath) { ... }
public Image fromJPG(String filePath) { ... }
public void toPNG(String filePath) { ... }
public Image fromPNG(String filePath) { ... }
public void toGIF(String filePath) { ... }
public Image fromGIF(String filePath) { ... }
}
Thay vào đó, tôi thường thích sử dụng một mẫu tương tự như sau:
public interface ImageSerializer
{
void serialize(Image src, Stream outputStream);
Image deserialize(Stream inputStream);
}
public class JPGImageSerializer : ImageSerializer
{
public void serialize(Image src, Stream outputStream) { ... }
public Image deserialize(Stream inputStream) { ... }
}
public class PNGImageSerializer : ImageSerializer
{
public void serialize(Image src, Stream outputStream) { ... }
public Image deserialize(Stream inputStream) { ... }
}
public class GIFImageSerializer : ImageSerializer
{
public void serialize(Image src, Stream outputStream) { ... }
public Image deserialize(Stream inputStream) { ... }
}
Bây giờ, tại thời điểm này, một trong những lưu ý với thiết kế này là các bộ nối tiếp cần phải biết identity
đối tượng mà nó được tuần tự hóa. Một số người sẽ nói rằng đây là thiết kế tồi, vì việc triển khai rò rỉ bên ngoài lớp học. Rủi ro / phần thưởng của việc này thực sự tùy thuộc vào bạn, nhưng bạn có thể điều chỉnh một chút các lớp để làm một cái gì đó như
public class Image
{
public void serializeTo(ImageSerializer serializer, Stream outputStream)
{
serializer.serialize(this.pixelData, outputStream);
}
public void deserializeFrom(ImageSerializer serializer, Stream inputStream)
{
this.pixelData = serializer.deserialize(inputStream);
}
}
Đây là một ví dụ chung, vì hình ảnh thường có siêu dữ liệu đi cùng với nó; những thứ như mức độ nén, không gian màu, vv có thể làm phức tạp quá trình.