में क्लास ट्रैकिंग के बिना व्युत्पन्न क्लास क्रमबद्धता बेस बेस पॉइंटर के माध्यम से व्युत्पन्न कक्षा को क्रमबद्ध करते समय मुझे बूस्ट क्रमबद्धता के साथ कुछ समस्याएं हैं। मुझे एक ऐसी प्रणाली की आवश्यकता है जो सिस्टम में प्राप्त होने वाली कुछ वस्तुओं को क्रमबद्ध करे, इसलिए मुझे समय के साथ क्रमबद्ध करने की आवश्यकता है। यह वास्तव में एक समस्या नहीं है क्योंकि मैं boost::archive::binary_oarchive
खोल सकता हूं और आवश्यकता होने पर वस्तुओं को क्रमबद्ध कर सकता हूं। तेजी से मैंने देखा कि बूस्ट मेमोरी एड्रेस द्वारा ऑब्जेक्ट ट्रैकिंग कर रहा था, इसलिए पहली समस्या यह थी कि उसी ऑब्जेक्ट को साझा करने वाले समय में अलग-अलग ऑब्जेक्ट्स को उसी ऑब्जेक्ट के रूप में सहेजा गया था। यह आवश्यक व्युत्पन्न वर्ग में निम्नलिखित मैक्रो का उपयोग द्वारा निर्धारित किया जा सकता है:बूस्ट (सी ++)
BOOST_CLASS_TRACKING(className, boost::serialization::track_never)
यह ठीक है, लेकिन फिर, जब आधार वर्ग सार नहीं है, आधार वर्ग ठीक से धारावाहिक नहीं है काम करता है। निम्नलिखित उदाहरण में, बेस क्लास क्रमबद्धता विधि को केवल पहली वस्तु के साथ बुलाया जाता है। निम्नलिखित में, बढ़ावा देता है कि इस ऑब्जेक्ट को पहले से क्रमबद्ध किया गया है हालांकि ऑब्जेक्ट के अलग-अलग प्रकार हैं।
#include <iostream>
#include <fstream>
#include <boost/serialization/export.hpp>
#include <boost/serialization/base_object.hpp>
#include <boost/serialization/list.hpp>
#include <boost/serialization/map.hpp>
#include <boost/serialization/vector.hpp>
#include <boost/serialization/shared_ptr.hpp>
#include <boost/archive/archive_exception.hpp>
#include <boost/archive/binary_oarchive.hpp>
#include <boost/archive/binary_iarchive.hpp>
using namespace std;
class AClass{
public:
AClass(){}
virtual ~AClass(){}
private:
double a;
double b;
//virtual void virtualMethod() = 0;
private:
friend class boost::serialization::access;
template<class Archive>
void serialize(Archive & ar, const unsigned int version)
{
ar & a;
ar & b;
cout << "A" << endl;
}
};
//BOOST_SERIALIZATION_ASSUME_ABSTRACT(Aclass)
//BOOST_CLASS_TRACKING(AClass, boost::serialization::track_never)
class BClass : public AClass{
public:
BClass(){}
virtual ~BClass(){}
private:
double c;
double d;
virtual void virtualMethod(){};
private:
friend class boost::serialization::access;
template<class Archive>
void serialize(Archive & ar, const unsigned int version)
{
ar & boost::serialization::base_object<AClass>(*this);
ar & c;
ar & d;
cout << "B" << endl;
}
};
// define export to be able to serialize through base class pointer
BOOST_CLASS_EXPORT(BClass)
BOOST_CLASS_TRACKING(BClass, boost::serialization::track_never)
class CClass : public AClass{
public:
CClass(){}
virtual ~CClass(){}
private:
double c;
double d;
virtual void virtualMethod(){};
private:
friend class boost::serialization::access;
template<class Archive>
void serialize(Archive & ar, const unsigned int version)
{
ar & boost::serialization::base_object<AClass>(*this);
ar & c;
ar & d;
cout << "C" << endl;
}
};
// define export to be able to serialize through base class pointer
BOOST_CLASS_EXPORT(CClass)
BOOST_CLASS_TRACKING(CClass, boost::serialization::track_never)
int main() {
cout << "Serializing...." << endl;
{
ofstream ofs("serialization.dat");
boost::archive::binary_oarchive oa(ofs);
for(int i=0;i<5;i++)
{
AClass* baseClassPointer = new BClass();
// serialize object through base pointer
oa << baseClassPointer;
// free the pointer so next allocation can reuse memory address
delete baseClassPointer;
}
for(int i=0;i<5;i++)
{
AClass* baseClassPointer = new CClass();
// serialize object through base pointer
oa << baseClassPointer;
// free the pointer so next allocation can reuse memory address
delete baseClassPointer;
}
}
getchar();
cout << "Deserializing..." << endl;
{
ifstream ifs("serialization.dat");
boost::archive::binary_iarchive ia(ifs);
try{
while(true){
AClass* a;
ia >> a;
delete a;
}
}catch(boost::archive::archive_exception const& e)
{
}
}
return 0;
}
जब कोड के इस टुकड़े को क्रियान्वित करने, परिणाम के रूप में अनुवर्ती है:
Serializing....
A
B
B
B
B
B
C
C
C
C
C
Deserializing...
A
B
B
B
B
B
C
C
C
C
C
तो आधार वर्ग केवल एक बार हालांकि व्युत्पन्न वर्ग स्पष्ट रूप track_never झंडा है धारावाहिक की जा रही है। इस व्यवहार को ठीक करने के लिए दो अलग-अलग कामकाज हैं। सबसे पहला बेस वर्चुअल वर्चुअल विधि के साथ मूल वर्ग सार बनाना और मैक्रो BOOST_SERIALIZATION_ASSUME_ABSTRACT(Aclass)
को कॉल करना है, और दूसरा एक बेस क्लास (कोड में टिप्पणी) में track_never ध्वज भी डालना है।
इनमें से कोई भी समाधान मेरी आवश्यकताओं को पूरा नहीं करता है, क्योंकि मैं सिस्टम राज्य के भविष्य के समयबद्ध क्रमिकरणों में करना चाहता हूं, जिसके लिए दिए गए डीसीएलएएस के लिए ट्रैकिंग सुविधाओं की आवश्यकता होगी (बी या सी नहीं), और एसीलास भी चाहिए अमूर्त नहीं है।
कोई संकेत? आधार वर्ग में ट्रैकिंग सुविधा से बचने के लिए स्पष्ट रूप से बेस क्लास क्रमबद्धता विधि को कॉल करने का कोई तरीका है (जिसे पहले ही व्युत्पन्न वर्ग में अक्षम कर दिया गया है)?
बढ़ावा दे सकता है ए को वर्चुअल होने के बावजूद वर्चुअल होने के लिए (मेरा मतलब है, बस 'BOOST_SERIALIZATION_ASSUME_ABSTRACT (एक्लास)' लाइन को असम्बद्ध करें और संकलित करने का प्रयास करें)? – Synxis