2010-05-14 14 views
27

मैंने हाल ही में सी ++ 0x में एक क्लास देखी है जो एक स्पष्ट डिफ़ॉल्ट कन्स्ट्रक्टर की मांग करता है। हालांकि, मैं ऐसे परिदृश्य के साथ आने में असफल रहा हूं जिसमें एक डिफ़ॉल्ट कन्स्ट्रक्टर को स्पष्ट रूप से बुलाया जा सकता है। यह एक निर्विवाद विनिर्देशक की तरह लगता है। मैंने सोचा कि शायद यह के पक्ष में Class c; को अस्वीकार कर देगा लेकिन ऐसा नहीं लगता है।स्पष्टीकरण डिफ़ॉल्ट डिफॉल्टर्स का उद्देश्य

C++ 0x FCD से कुछ प्रासंगिक उद्धरण, के बाद से यह आसान मुझे नेविगेट करने के लिए है [समान पाठ में मौजूद सी ++ 03, समान स्थानों में नहीं तो]

12.3.1.3 [ class.conv.ctor]

एक डिफ़ॉल्ट कन्स्ट्रक्टर एक स्पष्ट निर्माता हो सकता है; ऐसे कन्स्ट्रक्टर का उपयोग डिफ़ॉल्ट-प्रारंभिकरण या मूल्य प्रारंभिक (8.5) करने के लिए किया जाएगा।

यह एक स्पष्ट डिफ़ॉल्ट कन्स्ट्रक्टर का एक उदाहरण प्रदान करने के लिए आगे बढ़ता है, लेकिन यह बस ऊपर दिए गए उदाहरण की नकल करता है।

8.5.6 [decl.init]

प्रकार टी की एक वस्तु डिफ़ॉल्ट आरंभ करने के लिए इसका मतलब है:

- अगर टी (संभवत: सीवी-योग्य) वर्ग प्रकार है (धारा 9) , टी के लिए डिफ़ॉल्ट कन्स्ट्रक्टर कहा जाता है (और प्रारंभिकता बीमार है यदि टी के पास कोई सुलभ डिफ़ॉल्ट कन्स्ट्रक्टर नहीं है);

8.5.7 [decl.init]

के प्रकार टी का एक उद्देश्य मूल्य आरंभ कर देगा का अर्थ है:

- अगर टी एक साथ एक (संभवतः सीवी-योग्य) वर्ग प्रकार (धारा 9) है उपयोगकर्ता द्वारा प्रदत्त कन्स्ट्रक्टर (12.1), फिर टी के लिए डिफ़ॉल्ट कन्स्ट्रक्टर कहा जाता है (और प्रारंभिकता बीमार है यदि टी के पास कोई सुलभ डिफ़ॉल्ट कन्स्ट्रक्टर नहीं है);

दोनों मामलों में, डिफ़ॉल्ट कन्स्ट्रक्टर के लिए मानक कॉल कहा जाता है। लेकिन यह तब होगा जब डिफ़ॉल्ट कन्स्ट्रक्टर गैर-स्पष्ट था। पूर्णता खातिर:

8.5.11 [decl.init]

कोई प्रारंभकर्ता एक वस्तु के लिए निर्दिष्ट है, तो वस्तु डिफ़ॉल्ट-प्रारंभ होता है,

जो मैं बता सकता हूं, यह सिर्फ डेटा से रूपांतरण छोड़ देता है। जो समझ में नहीं आता है। सबसे अच्छा मैं के साथ आ सकता है निम्न होगा:

void function(Class c); 
int main() { 
    function(); //implicitly convert from no parameter to a single parameter 
} 

लेकिन जाहिर है कि जिस तरह से सी ++ डिफ़ॉल्ट तर्क संभालती नहीं है। से explicit Class(); अलग-अलग व्यवहार करने के लिए और क्या होगा?

इस प्रश्न को उत्पन्न करने वाला विशिष्ट उदाहरण std::function [20.8.14.2 func.wrap.func] था। इसके लिए कई कनवर्टिंग कन्स्ट्रक्टर की आवश्यकता होती है, जिनमें से कोई भी स्पष्ट रूप से चिह्नित नहीं है, लेकिन डिफ़ॉल्ट कन्स्ट्रक्टर है।

+0

जैसे ही मैंने पोस्ट मारा, मुझे लगता है कि मैं एक स्पष्टीकरण के साथ आया था। लेकिन मैं अपने संदेह की पुष्टि के लिए इंतजार करूंगा, क्योंकि यह किसी भी तरह से एक उपयोगी सवाल की तरह लगता है। –

उत्तर

21

यह एक स्पष्ट डिफ़ॉल्ट निर्माता वाणी:

struct A { 
    explicit A(int a1 = 0); 
}; 

A a = 0; /* not allowed */ 
A b; /* allowed */ 
A c(0); /* allowed */ 

मामले में कोई पैरामीटर नहीं है, निम्नलिखित उदाहरण की तरह, explicit अनावश्यक है।

A a = {}; /* error! */ 
A b{}; /* alright */ 

void function(A a); 
void f() { function({}); /* error! */ } 

लेकिन FCD में, वे changed this (हालांकि, मैं संदेह है कि:

struct A { 
    /* explicit is redundant. */ 
    explicit A(); 
}; 

कुछ C++ 0x मसौदा में, मैं विश्वास है कि यह n3035 था, यह निम्नलिखित तरीके से एक नई पहल की उनके पास इस विशेष कारण को ध्यान में नहीं था) कि सभी तीन मामलों संबंधित वस्तु मूल्य-प्रारंभिक वस्तु। मूल्य-प्रारंभिक अधिभार-रिज़ॉल्यूशन नृत्य नहीं करता है और इस प्रकार स्पष्ट रचनाकारों पर असफल नहीं होगा।

+0

ठीक है। फिर 'std :: function' के लिए स्पष्ट कन्स्ट्रक्टर ड्राफ्ट के उस संस्करण से बस एक पकड़ है? यह स्पष्टीकरण था कि आखिरकार मैंने प्रश्न लिखने के बाद पता लगाया, लेकिन न तो प्रदान किया गया उदाहरण और न ही 'std :: function()' ने एक वैकल्पिक पैरामीटर लिया, इसलिए मुझे पूरी तरह से विश्वास नहीं था। –

+0

ऐसा लगता है कि थोड़ा सा बदल गया है, [सीडब्ल्यूजी 1518] (http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_active.html#1518) देखें। जी ++ और क्लैंग ++ के हाल के संस्करण गैर-डिफॉल्ट स्पष्ट डिफॉल्ट कन्स्ट्रक्टर के लिए 'फ़ंक्शन ({}) को अस्वीकार करते हैं, यहां तक ​​कि C++ 11 मोड में भी। – dyp

+0

http://cplusplus.github.io/LWG/lwg-defects.html#2510 –

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