2009-08-26 16 views
11

मैं क्रमानुसार करने/unserialize निम्नलिखित वर्गों चाहते हैं:Boost.serialize के साथ व्युत्पन्न टेम्पलेट कक्षाओं को क्रमबद्ध कैसे करें?

class Feature{ 
... 
virtual string str()=0; 
}; 

template<typename T> 
class GenericFeature : public Feature{ 
T value; 
... 
virtual string str(); 
}; 

मैं boost.serialize डॉक्स पढ़ सकते हैं और सईद कि आप कक्षाएं रजिस्टर करना होगा। मैं उन्हें कन्स्ट्रक्टर में पंजीकृत कर सकता हूं। लेकिन लोडिंग में समस्याएं होंगी, क्योंकि पंजीकरण गतिशील होगा, स्थैतिक नहीं (जैसा कि मैंने समझा, आपको धारावाहिककरण/deserialization से पहले कक्षाओं को पंजीकृत करना होगा)।

इन प्रकार की कक्षाओं को कैसे सहेज/लोड करें?

उत्तर

15

पहले को बढ़ावा देने कि फ़ीचर सार है बताओ, हमेशा की जरूरत नहीं है:

BOOST_SERIALIZATION_ASSUME_ABSTRACT(Feature); 

क्रमबद्धता विधि इस तरह कम या ज्यादा दिखना चाहिए:

template<class Archive> 
void Feature::serialize(Archive & ar, const unsigned int version) 
{ 
    ar & BOOST_SERIALIZATION_NVP(some_member); 
} 


template<typename T,class Archive> 
void GenericFeature<T>::serialize(Archive & ar, const unsigned int version) 
{ 
    ar & boost::serialization::base_object<Feature>(*this); //serialize base class 
    ar & BOOST_SERIALIZATION_NVP(some_other_member); 
} 

अब मुश्किल बिंदु वर्ग रजिस्टर करने के लिए है serialize/deserialize में:

boost::archive::text_iarchive inputArchive(somesstream); 

boost::archive::text_oarchive outputArchive(somesstream); 

//something to serialize 
Feature* one = new GenericFeature<SomeType1>(); 
Feature* two = new GenericFeature<SomeType2>(); 
Feature* three = new GenericFeature<SomeType3>(); 

//register our class, must be all of posible template specyfication  
outputArchive.template register_type< GenericFeature<SomeType1> >(); 
outputArchive.template register_type< GenericFeature<SomeType2> >(); 
outputArchive.template register_type< GenericFeature<SomeType3> >(); 

// now simply serialize ;-] 
outputArchive << one << two << three; 

// register class in deserialization 
// must be the same template specification as in serialize 
// and in the same correct order or i'm get it wrong ;-D 
inputArchive.template register_type< GenericFeature<SomeType1> >(); 
inputArchive.template register_type< GenericFeature<SomeType2> >(); 
inputArchive.template register_type< GenericFeature<SomeType3> >(); 

Feature* another_one; 
Feature* another_two; 
Feature* another_three; 

// and deserialize ;-] 
inputArchive >> another_one >> another_two >> another_three; 

यदि आपको स्पष्ट पंजीकरण को छिपाने की आवश्यकता है ere और इसे और अधिक स्वचालित बनाते हैं, विशेष मज़ेदार टेम्पलेट बनाने का विचार है जो एक व्युत्पन्न वर्ग को पंजीकृत करता है, सभी उपलब्ध कराता है और एक सूची में डालता है, कि कक्षा फ़ीचर की एक स्थिर विधि उन सभी को पंजीकृत करेगी। हालांकि समस्या यह होगी कि आपको संग्रह के सभी संस्करणों के लिए पंजीकरण की आवश्यकता है, अभी मैं नहीं जानता कि पॉलिमॉर्फिक संग्रह नौकरी करेगा या नहीं।

+0

मुझे लगता है कि पहले कोड बॉक्स के लाइन 11 में एक बग है। अगर मुझे गलत नहीं लगता है, तो आपको "boost :: serialization :: base_object" के बाईं ओर "ar &" होना चाहिए। हालांकि अच्छा जवाब! –

+3

@lionbest: क्या आप 'बूस्ट :: serialization :: base_object (* यह) के बजाय 'BOOST_SERIALIZATION_BASE_OBJECT_NVP' का उपयोग नहीं करना चाहिए;' – Cookie

+0

मुझे लगता है कि यदि आप एक से अधिक बेस क्लास हैं तो आप नाम निर्दिष्ट करना चाहेंगे। मुझे नहीं लगता कि इस मैक्रो की आवश्यकता है, लेकिन यकीन है कि आप एक प्राप्त करना चाहते हैं। – Arpegius

संबंधित मुद्दे