जब मैं किसी वर्ग से ऑब्जेक्ट को तुरंत चालू करता हूं, तो जावा ऑप में ऑब्जेक्ट सहेजा जाता है। जब मैं ऑब्जेक्ट को क्रमबद्ध करके सहेजता हूं और बाद में मैं ऑब्जेक्ट को deserialize करता हूं, तो क्या मैं सही ढंग से समझता हूं कि ऑब्जेक्ट में अब एक नया ढेर पता होगा लेकिन फिर भी कक्षा का सटीक उदाहरण होगा।एक deserialised वस्तु मूल उदाहरण के रूप में एक ही उदाहरण है
उत्तर
अपने प्रश्न का उत्तर नहीं हो सकता बस एक हाँ या नहीं। अवधारणा का विश्लेषण करने के लिए आवश्यक है। मैं आपको एक पेंसिल और पेपर लेने का सुझाव दूंगा और इसे नीचे दिये गये बिंदुओं को ध्यान में रखकर स्वयं करूँगा।
- सभी जावा वस्तुओं जावा ढेर में बनाए जाते हैं (कुछ जो हैं के अलावा पूल में रखा लेकिन के लिए आप हम उन्हें अब के लिए छोड़ देगा सवाल)।
- जब एक वर्ग का एक उदाहरण नया कीवर्ड जोड़ते अक्रमांकन, क्लोन विधि या प्रतिबिंब एपीआई newInstance पद्धति का उपयोग करके बनाया जाता है, ढेर में एक नया अंतरिक्ष आरक्षित है और हम एक वस्तु संदर्भ (संदर्भ के हो सकते हैं के लिए असाइन करें ऑब्जेक्ट की कक्षा या ऑब्जेक्ट क्लास के सुपर कक्षाओं में से एक - फिर हम के लिए इस विवरण को अनदेखा कर सकते हैं)।
- जब आप अपनी ऑब्जेक्ट को सहेजते हैं, तो ऑब्जेक्ट की स्थिति नेस्टेड ऑब्जेक्ट्स से सहेजी जाती है।
- जब आप अपनी ऑब्जेक्ट को deserialize करते हैं, तो ऑब्जेक्ट एक नई प्रविष्टि ढेर में बनाएगा जिसमें किसी भी ऑब्जेक्ट का कोई संदर्भ नहीं होगा।
सभी वस्तु एक संदर्भ एक ढेर प्रविष्टि की ओर इशारा करते हैं और आप objectB.getObjectA() की कोशिश करता है, तो =:
संदर्भ आप में ऊपर अवधारणा picturizing के लिए नीचे दिए गए चित्र पर देखो = objectC.getObjectA() या कोई अन्य ऐसा ऑपरेशन, आप सच हो जाएंगे।
केस 1 जब आप वस्तुओं को अलग से बचाने और उन्हें यहाँ deserialize क्या ढेर में होता है:
अब आप पता लगा सकते हैं के रूप में है कि objectBcopy.getObjectA() == objectCcopy। getObjectA() ऑब्जेक्ट ए के संदर्भ के रूप में सही नहीं लौटाएगा कॉपी किए गए ऑब्जेक्ट्स के लिए कोई और नहीं है।
आप पता लगा सकते हैं के रूप में अब है कि:
केस 2 विपरीत, जब आप एक एकल फाइल में वस्तुओं को बचाने और उन्हें बाद में deserialize पर, यहाँ क्या ढेर में होता है objectBcopy.getObjectA() == objectCcopy.getObjectA() अब ऑब्जेक्ट के संदर्भ के रूप में सत्य होगा एक प्रति एक जैसी है, लेकिन यह अभी भी ऑब्जेक्ट ए की एक नई प्रति है।
मेरे कटौती का समर्थन करने के लिए एक त्वरित प्रोग्राम (केस 1 और केस 2):
public class Test{
public static void main (String args[]) throws IOException, ClassNotFoundException{
A a = new A();
B b = new B();
b.a = a;
C c = new C();
c.a = a;
System.out.println("b.a == c.a is " + (b.a == c.a));
// Case 1 - when two diferent files are used to write the objects
FileOutputStream fout = new FileOutputStream("c:\\b.ser");
ObjectOutputStream oos = new ObjectOutputStream(fout);
oos.writeObject(b);
oos.close();
fout.close();
fout = new FileOutputStream("c:\\c.ser");
oos = new ObjectOutputStream(fout);
oos.writeObject(c);
oos.close();
fout.close();
FileInputStream fileIn = new FileInputStream("c:\\b.ser");
ObjectInputStream in = new ObjectInputStream(fileIn);
B bCopy = (B) in.readObject();
in.close();
fileIn.close();
fileIn = new FileInputStream("c:\\c.ser");
in = new ObjectInputStream(fileIn);
C cCopy = (C) in.readObject();
in.close();
fileIn.close();
System.out.println("Case 1 - bCopy.a == cCopy.a is " + (bCopy.a == cCopy.a));
// Case 2 - when both the objects are saved in the same file
fout = new FileOutputStream("c:\\both.ser");
oos = new ObjectOutputStream(fout);
oos.writeObject(b);
oos.writeObject(c);
oos.close();
fout.close();
fileIn = new FileInputStream("c:\\both.ser");
in = new ObjectInputStream(fileIn);
bCopy = (B) in.readObject();
cCopy = (C) in.readObject();
in.close();
fileIn.close();
System.out.println("Case 2 - bCopy.a == cCopy.a is " + (bCopy.a == cCopy.a));
}
}
class A implements Serializable{
}
class B implements Serializable{
A a;
}
class C implements Serializable{
A a;
}
निम्नलिखित उत्पादन के साथ
:
b.a == c.a is true
Case 1 - bCopy.a == cCopy.a is false
Case 2 - bCopy.a == cCopy.a is true
"... लेकिन यह अभी भी ऑब्जेक्ट ए की एक नई प्रति है।" तो अगर मैं ऑब्जेक्ट ए कॉपी (उदा। आयु) का एक क्षेत्र बदलता हूं, तो ऑब्जेक्ट में परिवर्तन एक प्रति बीसीडीई के अंदर ऑब्जेक्ट ए (एस) में दिखाई नहीं देगी? –
यह सही है। चूंकि वस्तु एक अलग ढेर पते में है। अगर उत्तर ने आपकी मदद की, तो कृपया इसे स्वीकार करें। – Anshuman
उस स्थिति में, क्या आप एक तरीका सुझा सकते हैं ताकि मैं उपर्युक्त उदाहरण में सचित्र के रूप में जो हासिल करना चाहता हूं उसे पूरा कर सकूं? –
नहीं, सरल उत्तर यह है कि deserialized वस्तु स्मृति में एक ही उदाहरण नहीं होगा! यह इसके लिए नई मेमोरी आवंटित करेगा। http://www.javalobby.org/java/forums/t17491.html लिंक के माध्यम से भी जाएं जिसमें सिंगलटन के साथ deserialization का उपयोग कर ऑब्जेक्ट पुनर्प्राप्त करने का उदाहरण शामिल है! गहराई में readResolve() विधि के माध्यम से भी जाना, यह कुछ मामलों में सहायक होगा।
deserialized उदाहरण निश्चित रूप से मूल से एक विशिष्ट उदाहरण होगा, क्योंकि deserialized != original
में हमेशा सत्य होगा।
deserialized उदाहरण मूल उदाहरण के बराबर हो सकता है या नहीं, जैसा कि deserialized.equals(original)
में है। एक Serializable
वर्ग का एक उचित कार्यान्वयन के लिए, equals
शायद अक्रमांकन के बाद सच हो जाएगा, लेकिन यह एक वर्ग है जिसके लिए यह नहीं रखता है बनाने के लिए मामूली बात है:
class Pathological implements Serializable {
transient int value;
Pathological(int value) { this.value = value; }
@Override public int hashCode() { return value; }
@Override public boolean equals(Object other) {
if (other == this) { return true; }
if (other instanceof Pathological) {
return ((Pathological) other).value == this.value;
}
return false;
}
}
जब तक आप जब Pathological
निर्माण शून्य पारित करने के लिए होता है, उदाहरण serialization/deserialization के बाद बराबर नहीं होंगे, क्योंकि value
के मान को क्रमबद्ध नहीं किया जाएगा (क्योंकि यह क्षणिक है)।
नहीं वे स्मृति originalObj == deserilized
मेमोरी में एक ही वस्तु नहीं होंगे, हालांकि originalObj.equals(deserilized)
सत्य होना चाहिए।
ऑब्जेक्ट्स बी, सी, डी और ई। उन सभी को तत्काल, ऑब्जेक्ट ए था। फिर, मान लीजिए कि मैं उन सभी को क्रमबद्ध और deserialized। जब मैं deserialization के बाद ऑब्जेक्ट ए का एक क्षेत्र बदलता हूं, क्या बीसीडीई में ऑब्जेक्ट ए में ऐसे परिवर्तन को प्रतिबिंबित करने का कोई तरीका है?
तो मैं समझता हूँ कि आप सही तरीके से जवाब नहीं, संदर्भ में एक ही वस्तु एक
की ओर संकेत नहीं दिया जाएगा लेकिन अगर आप ऐसा चाहते हैं आप स्पष्ट रूप से प्रत्येक वस्तु में वस्तु एक के संदर्भ के सभी सेट कर सकते हैं बी, सी, डी और ई ऑब्जेक्ट ए
के समान उदाहरण को इंगित करने के लिए यहां दिए गए बिंदुओं को चित्रित करने के लिए एक डेमो है।
import java.io.*;
import java.util.*;
public class Demo {
public static void main(String... aArguments) {
List<Quark> quarks = Arrays.asList(
new Quark("up"), new Quark("down")
);
serialize(quarks);
List<Quark> recoveredQuarks = deserialize();
System.out.println(quarks == recoveredQuarks); // false
System.out.println(quarks.equals(recoveredQuarks)); // true
System.out.println(quarks.get(0) == recoveredQuarks.get(0)); // false
// but you can set it to the same instance
recoveredQuarks.set(0, quarks.get(0));
System.out.println(quarks.get(0) == recoveredQuarks.get(0)); // true
quarks.get(0).name = "Charm";
boolean b = quarks.get(0).name == recoveredQuarks.get(0).name;
System.out.println(b); // true
}
static void serialize(List<Quark> quarks) {
try {
OutputStream file = new FileOutputStream("quarks.ser");
OutputStream buffer = new BufferedOutputStream(file);
ObjectOutput output = new ObjectOutputStream(buffer);
output.writeObject(quarks);
output.close();
}
catch(IOException ex) { ex.printStackTrace(); }
}
static List<Quark> deserialize() {
List<Quark> recoveredQuarks = null;
try {
InputStream file = new FileInputStream("quarks.ser");
InputStream buffer = new BufferedInputStream(file);
ObjectInput input = new ObjectInputStream(buffer);
recoveredQuarks = (List<Quark>)input.readObject();
input.close();
}
catch(ClassNotFoundException ex){ }
catch(IOException ex){ ex.printStackTrace(); }
return recoveredQuarks;
}
}
class Quark implements Serializable {
String name;
Quark(String name) {
this.name = name;
}
@Override
public boolean equals(Object o) {
if (o != null && o instanceof Quark) {
return this.name.equals(((Quark)o).name);
}
return false;
}
}
serializing से पहले:
A originalA = ...;
B.a == C.a == D.a == E.a == originalA
सभी B.a
, C.a
, D.a
और A
, originalA
की इसी संदर्भ को E.a
बिंदु।
serializing और deserializing के बाद:
A otherA = ...;
B.a == C.a == D.a == E.a == otherA
सभी B.a
, C.a
, D.a
और A
, otherA
की इसी संदर्भ को E.a
बिंदु।
:
originalA != otherA
हालांकि
originalA.equals(otherA) == true
नोट:equals()
true
वापस आ जाएगी, बशर्ते यह वही ओवरराइडको लगातार जांच धारावाहिक क्षेत्रों के आधार पर समानता है। अन्यथा, यह वापसी false
हो सकता है।
संपादित करें:
सबूत:
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
public class Sample {
static class A implements Serializable {
private static final long serialVersionUID = 1L;
}
static class B implements Serializable {
private static final long serialVersionUID = 1L;
A a;
}
static class C implements Serializable {
private static final long serialVersionUID = 1L;
A a;
}
public static void main(String args[]) throws IOException, ClassNotFoundException {
A originalA = new A();
B b = new B();
b.a = originalA;
C c = new C();
c.a = originalA;
System.out.println("b.a == c.a is " + (b.a == c.a));
FileOutputStream fout = new FileOutputStream("ser");
ObjectOutputStream oos = new ObjectOutputStream(fout);
oos.writeObject(b);
oos.writeObject(c);
oos.close();
fout.close();
FileInputStream fileIn = new FileInputStream("ser");
ObjectInputStream in = new ObjectInputStream(fileIn);
B bDeserialized = (B) in.readObject();
C cDeserialized = (C) in.readObject();
in.close();
fileIn.close();
System.out.println("bDeserialized.a == cDeserialized.a is " + (bDeserialized.a == cDeserialized.a));
}
}
जबकि बराबर अनुबंध को हमेशा ओवरराइड करते समय देखा जाना चाहिए, यह सच नहीं लौटने के लिए आवश्यक नहीं है (आखिरकार, मूल ऑब्जेक्ट.क्वल्स भी इस अनुबंध को देखता है)। महत्वपूर्ण बात यह है कि बराबर उन क्षेत्रों की तुलना करता है जो धारावाहिक तंत्र द्वारा क्रमबद्ध/अनुक्रमित होते हैं, एक संगत तरीके से। –
- 1. ग # - वस्तु संदर्भ एक उदाहरण
- 2. केवल एक ही आवेदन उदाहरण
- 3. asyncio प्रतीक्षा करने योग्य वस्तु - मूल उदाहरण
- 4. Mockito thenReturn एक ही उदाहरण
- 5. मूल उदाहरण
- 6. एक उदाहरण
- 7. एक उदाहरण
- 8. उदाहरण उदाहरण के बिना एक सामान्य उदाहरण बनाने के लिए स्कैला में कोई तरीका है?
- 9. Django - मूल उदाहरण
- 10. एकाधिक साइडकीक उदाहरण एक ही कतार
- 11. एक ही उदाहरण पर एकाधिक कार्यकर्ता भूमिकाएं
- 12. उदाहरण के लिए मूल कोड
- 13. एंड्रॉइड: एक ही समय में मीडिया रिकॉर्डर के दो उदाहरण
- 14. कैसे एक ही वस्तु
- 15. एक उदाहरण विधि
- 16. एक प्रतिदेय उदाहरण
- 17. एक उदाहरण विधि का उदाहरण? (जावा)
- 18. एक मौजूदा आइट्यून्स उदाहरण
- 19. एक इंटरफेस के साथ उदाहरण
- 20. एक ही प्रोग्राम के दो उदाहरण चलाना कैसे अवरुद्ध करें?
- 21. जब एकाधिक स्प्रिंग सिंगलटन उदाहरण एक ही समय में
- 22. कैसे एक पहले से ही निर्मित वस्तु पुनर्निमित किया जा सकता है (उदाहरण देखें)
- 23. एक पीईक्यूटी उदाहरण प्रोग्राम के बारे में
- 24. केवल एक आवेदन उदाहरण
- 25. क्या थ्रेड। कंटेंट थ्रेड हमेशा एक ही उदाहरण लौटाता है?
- 26. CodeMirror एक संपादक उदाहरण
- 27. एक अपाचे उदाहरण
- 28. क्या वाक्य रचना स्यूडोकोड में एक उदाहरण के रूप जावा
- 29. एक ही वस्तु एक ManyToManyField
- 30. उदाहरण के लिए एक अच्छा अभ्यास है?
originalObj == deserilized झूठी हो जाएगा लेकिन originalObj.equals (deserilized) सच होना चाहिए। – robbmj
यदि मैं आपको सही ढंग से समझता हूं तो उत्तर नहीं है, तो दो संदर्भ एक ही ऑब्जेक्ट ए – robbmj
पर इंगित नहीं करेंगे यदि आप अपना प्रश्न विस्तृत करना चाहते हैं, तो टिप्पणियों में ऐसा न करें, इसे प्रश्न के मुख्य भाग में करें। टिप्पणियां लंबी चर्चाओं या कोड या प्रारूपित किसी भी स्थान के लिए एक जगह नहीं हैं। – RealSkeptic