आपका परीक्षण सेट एक ऑफ साइट लिंक पर है और अपने मूल पोस्ट के बाद से विविध है, इसलिए मैं शब्दशः परीक्षण सेट के बारे में मैं बात कर रहा हूँ की प्रतिलिपि बनाएगा यहाँ:
:
static_assert(is_explicitly_convertible< double, double >::value, "1");
static_assert(is_explicitly_convertible< double &, double >::value, "2");
static_assert(is_explicitly_convertible< double const, double >::value, "3");
static_assert(is_explicitly_convertible< double const &, double >::value, "4");
static_assert(is_explicitly_convertible< double, double const & >::value, "5");
static_assert(is_explicitly_convertible< double &, double const & >::value, "6");
static_assert(is_explicitly_convertible< double const, double const & >::value, "7");
static_assert(is_explicitly_convertible< double const &, double const & >::value, "8");
static_assert(!is_explicitly_convertible< double, double & >::value, "9"); // not a ref
static_assert(is_explicitly_convertible< double &, double & >::value, "10");
static_assert(!is_explicitly_convertible< double const, double & >::value, "11");
static_assert(!is_explicitly_convertible< double const &, double & >::value, "12");
static_assert(is_explicitly_convertible< double, double const >::value, "13");
static_assert(is_explicitly_convertible< double &, double const >::value, "14");
static_assert(is_explicitly_convertible< double const, double const >::value, "15");
static_assert(is_explicitly_convertible< double const &, double const >::value, "16");
static_assert(is_explicitly_convertible< AA const &, A const & >::value, "=&1.a");
static_assert(is_explicitly_convertible< CC const &, C const & >::value, "=&1.b");
static_assert(is_explicitly_convertible< BB const &, B const & >::value, "=&1.c");
static_assert(!is_explicitly_convertible< AA const &, A & >::value, "&1.a");
static_assert(!is_explicitly_convertible< CC const &, C & >::value, "&1.b");
static_assert(!is_explicitly_convertible< BB const &, B & >::value, "&1.c");
static_assert(is_explicitly_convertible< AA const, A const & >::value, "=1.a");
static_assert(is_explicitly_convertible< CC const, C const & >::value, "=1.b");
static_assert(is_explicitly_convertible< BB const, B const & >::value, "=1.c");
//static_assert(!is_explicitly_convertible< AA const, A >::value, "=2.a"); // ???????????????
//static_assert(!is_explicitly_convertible< CC const, C >::value, "=2.b");
//static_assert(!is_explicitly_convertible< BB const, B >::value, "=2.c");
static_assert(!is_explicitly_convertible< AA const, A & >::value, "=3.a"); // good!
static_assert(!is_explicitly_convertible< CC const, C & >::value, "=3.b"); //
static_assert(!is_explicitly_convertible< BB const, B & >::value, "=3.c"); //
static_assert(!is_explicitly_convertible< AA const, A && >::value, "=4.a"); // not interesting
static_assert(!is_explicitly_convertible< CC const, C && >::value, "=4.b"); //
static_assert(!is_explicitly_convertible< BB const, B && >::value, "=4.c"); //
static_assert(!is_explicitly_convertible< AA const, B const & >::value, "=5.a");
static_assert(!is_explicitly_convertible< AA const, C const & >::value, "=5.b");
static_assert(!is_explicitly_convertible< BB const, A const & >::value, "=5.c");
static_assert(!is_explicitly_convertible< BB const, C const & >::value, "=6.a");
static_assert(!is_explicitly_convertible< CC const, A const & >::value, "=6.b");
static_assert(!is_explicitly_convertible< CC const, B const & >::value, "=6.c");
static_assert(!is_explicitly_convertible< AA const, B & >::value, "=7.a");
static_assert(!is_explicitly_convertible< AA const, C & >::value, "=7.b");
static_assert(!is_explicitly_convertible< BB const, A & >::value, "=7.c");
static_assert(!is_explicitly_convertible< BB const, C & >::value, "=8.a");
static_assert(!is_explicitly_convertible< CC const, A & >::value, "=8.b");
static_assert(!is_explicitly_convertible< CC const, B & >::value, "=8.c");
static_assert(!is_explicitly_convertible< AA const, B >::value, "=9.a"); // very subtle moment (see class AA above)
static_assert(!is_explicitly_convertible< AA const, C >::value, "=9.b");
static_assert(is_explicitly_convertible< BB const, A >::value == std::is_constructible< A, A && >::value, "=9.c"); // (see class BB above)
static_assert(!is_explicitly_convertible< BB const, C >::value, "=10.a");
static_assert(!is_explicitly_convertible< CC const, A >::value, "=10.b");
static_assert(!is_explicitly_convertible< CC const, B >::value, "=10.c");
static_assert(is_explicitly_convertible< AA, A & >::value, "~1.a");
static_assert(is_explicitly_convertible< CC, C & >::value, "~1.b");
static_assert(is_explicitly_convertible< BB, B & >::value, "~1.c");
//static_assert(!is_explicitly_convertible< AA, A >::value, "~2.a"); // ???????????????
//static_assert(!is_explicitly_convertible< CC, C >::value, "~2.b");
//static_assert(!is_explicitly_convertible< BB, B >::value, "~2.c");
static_assert(is_explicitly_convertible< AA, A const & >::value, "~3.a"); // convertible
static_assert(is_explicitly_convertible< CC, C const & >::value, "~3.b"); //
static_assert(is_explicitly_convertible< BB, B const & >::value, "~3.c"); //
static_assert(!is_explicitly_convertible< AA, B const & >::value, "~4.a");
static_assert(!is_explicitly_convertible< AA, C const & >::value, "~4.b");
static_assert(!is_explicitly_convertible< BB, A const & >::value, "~4.c");
static_assert(!is_explicitly_convertible< BB, C const & >::value, "~5.a");
static_assert(!is_explicitly_convertible< CC, A const & >::value, "~5.b");
static_assert(!is_explicitly_convertible< CC, B const & >::value, "~5.c");
static_assert(std::is_convertible< double, double const & >::value, "5*");
static_assert(!std::is_convertible< double, double & >::value, "9*");
आप जीसीसी 4.7.2 (और शायद पहले, मैं जांच न की हो) का लाभ उठाने तो सी ++ 11 स्टैंडर्ड लाइब्रेरी समस्या का हल
<type_traits>
हालांकि में परिभाषित किया गया है, तो आप सी ++ 11 स्टैंडर्ड लाइब्रेरी के उस संस्करण में एक error का लाभ उठाने की जाएगी। यह विशेषता टेम्पलेट वहां नहीं होना चाहिए था, क्योंकि इसे N3047 (2010) के अनुसार मानक से हटा दिया गया था।
यदि आप जीसीसी 4.8.1 (या शायद 4.8; मैंने चेक नहीं किया है) पर है तो यह विशेषता लाइब्रेरी में अब नहीं है, और यदि आप चाहते हैं तो आपको फिर से अपना रोल करना होगा।
लेकिन यह केवल एक शुरुआत के लिए जीसीसी 4.7.2 के <type_traits>
में परिभाषा का निरीक्षण करने के लिए मानव होगा, और है कि कर पता चलता है कि जीएनयू implementer माना विशेषता लेकिन std::is_constructible<To,From>
का प्रतिलोम कुछ भी नहीं होने के लिए:
/// is_explicitly_convertible
template<typename _From, typename _To>
struct is_explicitly_convertible
: public is_constructible<_To, _From>
{ };
कोई भी सोच सकता है: लेकिन ज़ाहिर है।
तो ऐसा क्यों नहीं चल रहा है? एन 3047 बताता है:
शेष प्रश्न यह है कि जिस तरह से is_explicitly_convertible
विशेषता भी प्रभावित की जानी चाहिए।बुनियादी विकल्प हैं:
- वर्तमान static_cast अभिव्यक्ति की ओर लौटने, अब
is_constructible
पर is_explicitly_convertible
निर्भर बनाकर फिक्स is_explicitly_convertible
।
- मानक से
is_explicitly_convertible
हटाएं।
पहली पसंद पर विचार किया गया था, लेकिन यह पता चला कि "स्पष्ट रूप से परिवर्तनीय" वास्तव में क्या मतलब होना चाहिए, इसकी काफी अलग-अलग समझ है। जबकि कुछ मानते हैं कि static_cast
सही ढंग से इसे व्यक्त करता है, अन्य लोगों का मानना है कि निश्चित is_constructible
is_explicitly_convertible
के लिए भी बेहतर अर्थ प्रदान करेगा। इसलिए यह पत्र कार्य ड्राफ्ट से is_explicitly_convertible
को हटाने की सिफारिश करता है। इसे अब कोई नुकसान नहीं करना चाहिए, क्योंकि कुछ भी उस विशेष परिभाषा पर निर्भर नहीं है। और यदि यह पता चला है कि यह विशेषता अभी भी उपयोगी होगी, तो इसे मानक के एक और संशोधन में जोड़ा जा सकता है।
कि परिभाषा कोई ज्ञात बग था, लेकिन वहाँ के रूप में है कि क्या की "स्पष्ट रूप से परिवर्तनीय" अर्थ है कि यह codifies सही एक है का विरोध भी दृश्य नहीं थे: -
- डी 1)
From
है स्पष्ट रूप से To
= df To
के लिए परिवर्तनीय From
- डी 2 से constructible)
From
स्पष्ट To
= df From
के लिए परिवर्तनीय स्थिरको ढाला जा सकता है
मैं इस विवाद (मैं भी बाहर काम नहीं किया कि क्या अंतर है, अपने आप को), लेकिन है कि आप बस अपने पैसे का भुगतान और अपनी पसंद ले सुझाव देगा करने के लिए बहस नहीं होगी।
यदि आप डी 1 का पक्ष लेते हैं) तो आप उपरोक्त के रूप में जीसीसी 4.7.2 <type_traits>
पर से विशेषता की परिभाषा ले सकते हैं।
यदि आप डी 2 का पक्ष लेते हैं, तो आप gcc 4.8.1 <type_traits>
से std::is_convertible<From,To>
की परिभाषा को चोरी और अनुकूलित कर सकते हैं। यह परिभाषा आंतरिक सहायक कार्यों को आमंत्रित करती है जिन्हें आपको ट्रैक करना होगा।अनुकूलन आप चाहेगा From
के लिए बदलने के लिए From
के लिए SFINAE परीक्षण परोक्ष एक परीक्षण करने के लिए To
लिए डाली जा सकती है static_cast
To
हो सकता है हो सकता है; और उस का मतलब होगा की जगह:
साथ
template<typename _From1, typename _To1>
static decltype(__test_aux<_To1>(std::declval<_From1>()), __one())
__test(int);
:
template<typename _From1, typename _To1>
static decltype(__test_aux<_To1>(static_cast<_To1>(std::declval<_From1>())), __one())
__test(int);
इस परिभाषा के एक कट-डाउन संस्करण ( From
के रूप में इस तरह के मामलों की अनदेखी की जा रही void
और To
एक समारोह या सरणी प्रकार किया जा रहा है), जो आपके static_assert
एस में परीक्षण किए गए प्रकारों के लिए करेगा:
template<typename From, typename To>
struct is_explicitly_convertible
{
template<typename T>
static void f(T);
template<typename F, typename T>
static constexpr auto test(int) ->
decltype(f(static_cast<T>(std::declval<F>())),true) {
return true;
}
template<typename F, typename T>
static constexpr auto test(...) -> bool {
return false;
}
static bool const value = test<From,To>(0);
};
या तो डी 1 परिभाषा या कट-डाउन डी 2 परिभाषा आपके सभी static_assert
एस के 63 में से एक को बनाए रखती है। (मैं ++ जी के साथ 4.7.2 और 4.8.1, -g;-O0;-Wall;-std=c++11
संकलित, और भी -std=gnu++1y
कि आप कार्यरत साथ)
आपका नवीनतम समाधान पता चलता है कि आप एक अलग के साथ डी 2 स्कूल के लिए अपने अपने तरीके से बना दिया है, कार्यान्वयन की शैली।
दो के
, जब तक मैं कुछ इसके साथ गलत लगता है, मैं, डी 1 परिभाषा पसंद करेंगे प्रति जीसीसी 4.7.2 के रूप में है, क्योंकि केवल यह बहुत सरल है और विशेष रूप से std::is_constructible
की एक छोटी सी व्युत्पन्न है।
शायद मैं इस सवाल को गलत समझ रहा हूं, लेकिन आप 'dynamic_cast (FROM & val)' कर सकते हैं, यदि रूपांतरण योग्य नहीं है तो यह 'std :: bad_cast' फेंक देगा। –
@ एच 2CO3 मान लीजिए, यह प्रश्न संकलन समय के मुद्दे के बारे में है। – Orient
जैसा कि आप एक स्पष्ट रूपांतरण ऑपरेटर की जांच करना चाहते हैं, आपका कार्य नीचे उबालता प्रतीत होता है [यह निर्धारित करना कि कक्षा टी के पास दिए गए हस्ताक्षर के साथ सदस्य कार्य है या नहीं) (http://stackoverflow.com/q/87372/1362568)। मेरे कई में से कई उत्तर हैं। –