मैं ऐसी परिस्थिति में हूं जहां मेरे पास दो वर्गों की परिभाषाओं के बीच एक परिपत्र निर्भरता पाश है, जहां तक (जहां तक मैं कह सकता हूं) दोनों वर्गों को अन्य प्रकारों को सही तरीके से परिभाषित करने के लिए एक पूर्ण प्रकार की आवश्यकता होती है।आकार लेने के लिए व्यावहारिक रूप से सुरक्षित (std :: unordered_map <std :: string, T>) सभी टी के लिए समान है?
सरल शब्दों में, मैं क्या क्या चल रहा है की सरलीकृत संस्करण की आवश्यकता है:
struct Map;
struct Node {
// some interface...
private:
// this cannot be done because Map is an incomplete type
char buffer[sizeof(Map)];
// plus other stuff...
void* dummy;
};
struct Map {
// some interface...
private:
// this is Map's only member
std::unordered_map<std::string, Node> map_;
};
स्थिति, ऊपर से वास्तव में अधिक जटिल है Node
के बाद से वास्तव में एक प्रकार का प्रकार (boost::variant
के समान होने जा रहा है) जो प्रीलोकेटेड (और उचित संरेखण के साथ, जिसे मैं इस सरलीकरण में अनदेखा कर रहा हूं) में स्पष्ट रूप से एकाधिक प्रकार की वस्तुओं में से एक को बनाने के लिए प्लेसमेंट नया का उपयोग करता हूं: बफर इसलिए sizeof(Map)
नहीं बल्कि कुछ गणना की स्थिरता पर निर्भर है sizeof(Map)
।
समस्या यह है कि sizeof(Map)
उपलब्ध नहीं है जब Map
केवल आगे घोषित किया गया है। इसके अलावा, अगर मैं Node
पहले घोषित करने के लिए घोषणाओं का क्रम बदलता हूं, तो Map
का संकलन विफल रहता है, std::unordered_map<std::string, Node>
को तत्काल नहीं किया जा सकता है जब Node
कम से कम एक अपूर्ण प्रकार है, कम से कम उबंटू पर मेरे जीसीसी 4.8.2 के साथ।
struct Node {
// some interface...
private:
// doing this instead of depending on sizeof(Map)
char buffer[sizeof(std::unordered_map<std::string, void*>)];
// other stuff...
void* dummy;
};
struct Map {
// some interface...
private:
// this is Map's only member
std::unordered_map<std::string, Node> map_;
};
// and asserting this after the fact to make sure buffer is large enough
static_assert (sizeof(Map) <= sizeof(std::unordered_map<std::string, void*>),
"Map is unexpectedly too large");
: (मैं इसे libstdc पर निर्भर करता है ++ संस्करण जीसीसी संस्करण की तुलना में अधिक पता है, लेकिन मैं आसानी से नहीं पता है कि खोजने के लिए कैसे ...)
एक विकल्प के रूप में, मैं निम्नलिखित तरीके को पर विचार कर रहा हूँ
यह मूल रूप से इस धारणा पर निर्भर करता है कि std::unordered_map<std::string, T>
सभी टी के लिए समान आकार है, जो कि जीसीसी का उपयोग करके मेरे परीक्षण से सच है।
मेरा प्रश्न इस प्रकार तीन गुना है:
वहाँ सी ++ मानक में कुछ भी है की आवश्यकता है कि है कि यह धारणा सही पकड़ करने के लिए? (मुझे पता नहीं यह सोचते हैं हूँ, लेकिन अगर वहाँ मैं सुखद आश्चर्य होगा ...)
यदि नहीं, तो यह है व्यावहारिक रूप से सुरक्षित यह वैसे भी सभी उचित कार्यान्वयन के लिए सच है ग्रहण करने के लिए, और कहा कि स्थिर अभिकथन मेरे संशोधित संस्करण में कभी आग नहीं होगी?
अंत में, क्या इस मुद्दे पर कोई बेहतर कामकाज है जिसे मैंने नहीं सोचा है? मुझे यकीन है कि यह वहाँ स्पष्ट कुछ मैं बजाय कर सकते हैं कि मैं के बारे में सोचा नहीं किया है, लेकिन दुर्भाग्य से मैं कुछ भी नहीं सोच सकते हैं संभव है हूँ ...
टिप्पणियां विस्तारित चर्चा के लिए नहीं हैं; यह वार्तालाप [चैट करने के लिए स्थानांतरित हो गया है] (http://chat.stackoverflow.com/rooms/77815/discussion-on-question-by-trantorian- व्यावहारिक रूप से-safe-to-assume-sizeofstdunor)। – Taryn