मुझे std::is_constructible<void()>::value
के लिए असंगत परिणाम मिल रहे हैं। मानक की मेरी व्याख्या यह है कि यह गलत होना चाहिए। हालांकि, Clang, libC++ और libstdC++ * दोनों के साथ, सच देता है। जीसीसी और एमएसवीसी दोनों झूठे देते हैं। कौन सा परिणाम सही है?std :: is_constructible <void()> :: मान का सही परिणाम क्या है?
Standardese
यहाँ standardese है, N4527 [meta.unary.prop]/7:
को देखते हुए निम्नलिखित समारोह घोषणा:
template <class T> add_rvalue_reference_t<T> create() noexcept;
एक टेम्पलेट के लिए विधेय हालत विशेषज्ञता
is_constructible<T, Args...>
संतुष्ट होगा अगर केवल निम्नलिखित चर परिभाषा के लिए अच्छी तरह से गठित किया जाएगा टेड चरt
:T t(create<Args>()...);
नोट: यह पाठ से सी ++ 11 (N3485), जहां create
noexcept
चिह्नित नहीं किया गया था थोड़ा बदल दिया है। हालांकि, इसके लिए लेखांकन करते समय मेरे परीक्षणों के नतीजे नहीं बदले।
टेस्ट केस
यहाँ दोनों प्रकार विशेषता और standardese परिभाषा के अपने न्यूनतम परीक्षण का मामला है:
#include <type_traits>
static_assert(std::is_constructible<void()>::value, "assertion fired");
template<typename T>
std::add_rvalue_reference_t<T> create() noexcept;
template<typename T, typename... Args>
void foo() {
T t(create<Args>()...);
}
int main() {
foo<void()>();
}
परिणाम:
- स्थिर अभिकथन PASSED
foo<void()>
संकलन नहीं किया
- स्थिर अभिकथन PASSED
foo<void()>
GCC (HEAD, libstdc++) संकलन नहीं किया:
- स्थिर दावे विफल
foo<void()>
MSVC संकलन नहीं था (संस्करण 19 http://webcompiler.cloudapp.net/ के माध्यम से):
- स्थिर दावे विफल
foo<void()>
संकलन नहीं था (स्थिर अभिकथन बाहर टिप्पणी की आवश्यकता है)
* __GLIBCXX__
परिभाषित नहीं किया गया है जब क्लैंग का उपयोग -stdlib
विकल्प और -stdlib=libstdc++
के साथ किया जाता है। मुझे यकीन है कि libstdC++ वास्तव में उपयोग किया जा रहा है या नहीं। यदि मानक की मेरी व्याख्या सही है, तो मुझे यकीन है कि यह क्लैंग या libC++ के साथ एक बग है या नहीं।
देखें [एलडब्लूजी 2560] (http://wg21.link/lwg2560) और [क्लैंग बग 25513] (https://llvm.org/bugs/show_bug.cgi?id=25513)। –
@ टी.सी., धन्यवाद! यह देखने के लिए अच्छा है। – chris