مشخصات مقاله
-
0
-
0.0
-
6953
-
0
-
0
آموزش Java-آموزش Serialization در جاوا
جاوا مکانیزمی به نام توالی آبجکت (object serialization) ارائه می دهد که در آن آبجکت می تواند به عنوان دنباله ای از بایت ها ارائه شود که حاوی آبجکت داده به همراه اطلاعاتی در مورد نوع آبجکت و نوع داده ی ذخیره شده در آبجکت می باشد.
پس از اینکه یک آبجکت دنباله دار در یک فایل نوشته شد، این آبجکت از فایل خوانده می شود و از این حالت توالی خارج می شود (deserialized) که نوع اطلاعات و بایت هایی که آبجکت را نمایش می دهد و داده ی آن می تواند برای ایجاد مجدد آبجکت در حافظه استفاده شود.
تاثیر گذارتر این است که کل فرایند مستقل از JVM می باشد، بدین معنا که یک آبجکت می تواند روی یک سکو به حالت دنباله دار درآید و روی بخشی کاملا متفاوت از سکو از این حالت خارج شود.
گروه های ObjectInputStream و ObjectOutputStream جریان های سطح بالایی هستند که حاوی متودهایی برای دنباله دار کردن و یا غیردنباله دار کردن یک آبجکت استفاده می شوند.
گروه ObjectOutputStream حاوی متودهای مختلفی برای نوشتن انواع مختلف داده می باشد، اما یک متود خاص همیشه مشخص می ماند:
public final void writeObject(Object x) throws IOException
متود بالا یک آبجکت را دنباله دار کرده و آن را به جریان خروجی ارسال می کند. به طور مشابه گروه ObjectInputStream حاوی متود زیر برای خارج کردن یک آبجکت از حالت دنباله دار استفاده می شود (deserializing).
public final Object readObject() throws IOException,
ClassNotFoundException
این متود آبجکت بعدی را از جریان بیرون کشیده آن را deserialize می کند. مقدار گزارش شده Object می باشد، بنابراین شما باید آن را به نوع داده ی مناسب خود اختصاص دهید.
برای توضیح چگونگی دنباله دار کردن آبجکت در جاوا، قصد دارم از گروه Employee استفاده کنم که قبلا در مورد آن بحث کردیم. فرض کنید که ما گروه Employee زیر را در اختیار داریم که اینترفیس Serializable را اجرا می کند.
public class Employee implements java.io.Serializable
{
public String name;
public String address;
public transient int SSN;
public int number;
public void mailCheck()
{
System.out.println("Mailing a check to " + name
+ " " + address);
}
}
دقت داشته باشید که برای یک گروه که به طور موفقیت آمیز دنباله دار می شود، دو شرط باید در نظر گرفته شوند:
· گروه باید اینترفیس java.io.Serializable را اجرا کند.
· همه ی فیلدها در گروه باید serializable باشند. اگر یک فیلد serializable نباشد، باید به عنوان موقت در نظر گرفته شود.
اگر شما مشتاقید بدانید که یک گروه استاندارد جاوا serializable است یا نه، داکیومنت ها را برای گروه چک کنید. تست بسیار ساده می باشد: اگر گروه java.io.Serializable را اجرا می کند، بنابراین serializable می باشد، در غیر این صورت اینطور نیست.
دنباله دار کردن یک آبجکت:
گروه ObjectOutputStream برای دنباله دار کردن یک آبجکت استفاده می شود. برنامه ی SerializeDemo زیر یک آبجکت Employee را نمونه گذاری کرده و آن را به شکل یک فایل سریالی در می آورد.
وقتی اجرای برنامه انجام می شود، فایلی به نام employee.ser ایجاد می شود. برنامه هیچ خروجی تولید نمی کند، اما کد را بررسی کرده و سعی می کند مشخص کند که برنامه در حال انجام چه کاریست.
نکته: در هنگام تبدیل یک آبجکت به یک فایل، تبدیل استاندارد در جاوا این است که به فایل یک .serextension داده شود.
import java.io.*;
public class SerializeDemo
{
public static void main(String [] args)
{
Employee e = new Employee();
e.name = "Reyan Ali";
e.address = "Phokka Kuan, Ambehta Peer";
e.SSN = 11122333;
e.number = 101;
try
{
FileOutputStream fileOut =
new FileOutputStream("/tmp/employee.ser");
ObjectOutputStream out = new ObjectOutputStream(fileOut);
out.writeObject(e);
out.close();
fileOut.close();
System.out.printf("Serialized data is saved in /tmp/employee.ser");
}catch(IOException i)
{
i.printStackTrace();
}
}
}
Deserialize کردن یک آبجکت:
برنامه ی DeserializeDemo زیر آبجکت Employee ایجاد شده در برنامه ی SerializeDemo را deserialize می کند. برنامه را مطالعه کرده و سعی کنید خروجی را تعیین کنید:
import java.io.*;
public class DeserializeDemo
{
public static void main(String [] args)
{
Employee e = null;
try
{
FileInputStream fileIn = new FileInputStream("/tmp/employee.ser");
ObjectInputStream in = new ObjectInputStream(fileIn);
e = (Employee) in.readObject();
in.close();
fileIn.close();
}catch(IOException i)
{
i.printStackTrace();
return;
}catch(ClassNotFoundException c)
{
System.out.println("Employee class not found");
c.printStackTrace();
return;
}
System.out.println("Deserialized Employee...");
System.out.println("Name: " + e.name);
System.out.println("Address: " + e.address);
System.out.println("SSN: " + e.SSN);
System.out.println("Number: " + e.number);
}
}
این برنامه نتیجه ی زیر را به دنبال دارد:
Deserialized Employee...
Name: Reyan Ali
Address:Phokka Kuan, Ambehta Peer
SSN: 0
Number:101
در اینجا نکات مهمی وجود دارند که باید ذکر شوند:
· گروه try/catch سعی می کند که یک ClassNotFoundException را بگیرد که توسط متود readObject() اعلام شده است. برای اینکه یک JVM قادر باشد یک آبجکت را deserialize کند، باید بتواند bytecode را برای گروه پیدا کند. اگر JVM در طی deserialization کردن یک آبجکت نتواند یک گروه را پیدا کند، یک ClassNotFoundException وارد می کند.
· دقت داشته باشید که مقدار گزارش شده از readObject() بخشی از یک مرجع Employee می باشد.
· وقتی که آبجکت به حالت سریالی در آمد، مقدار فیلد SSN عدد 11122333 بود، اما به خاطر اینکه فیلد موقت است، این مقدار به جریان خروجی ارسال نشد. فیلد SSN از آبجکت deserialized Employee مقدار 0 می باشد.