2015-09-04 51 views
1

在下面的代碼片段中,我試圖確定一個類是否有一個副本ctor或不。 如果我的班級沒有副本,我只會看到一個編譯錯誤。我無法讓它返回真或假。請幫助我..檢查一個班級是否有副本?返回true或false

template <typename T> 
auto has_copy_ctor(T const& data) -> decltype(T(data), bool()) 
{ 
    return true; 
} 

struct A 
{ 
    A(A const& obj) = delete; 
}; 

struct B {}; 

int main() 
{ 
    std::cout << has_copy_ctor<B>(B{}) << std::endl; // compiles 
    std::cout << has_copy_ctor<A>(A{}) << std::endl; // does not compile 
} 

回答

3

考慮使用std::is_copy_constructible

SFINAE表示無法替換的模板不是錯誤,但如果沒有模板匹配,您仍然有錯誤。在你的情況下,你需要第二個模板函數,它對於不可複製構造的類返回false。

在libC++中,is_copy_constructible是使用__is_constructible非標準編譯器內在實現的。由於這些都保持在最低限度,因此如果可能的話,「本地C++」實現可能不是微不足道的。

+0

*「由於這些是保持在最低水平,機會是一個‘原生C++’的實施將是不平凡的,如果在所有的p 「*,[爲什麼不?](http://coliru.stacked-crooked.com/a/1f66e255907a205c) –

+0

嗯,我想我不是很有想象力。 – zneak

+0

嗯,我更感興趣的是瞭解SFINAE的其他部分,我想不出來...我仍然接受你的答案。 – gjha

1

您可以使用std::is_copy_constructible

int main() 
{ 
    std::cout << std::is_copy_constructible<B>::value << std::endl; 
    std::cout << std::is_copy_constructible<A>::value << std::endl; 
} 
2

下面是你可以擴展你的方法(用函數模板)來檢查類型是否是拷貝構造(在一個世界裏<type_traits>不可用):

#include <utility> 

template <typename T> 
constexpr auto has_copy_ctor(int) 
    -> decltype(T(std::declval<const T&>()), void(), bool()) 
{ 
    return true; 
} 

template <typename T> 
constexpr bool has_copy_ctor(char) 
{ 
    return false; 
} 

template <typename T> 
constexpr bool has_copy_ctor() 
{ 
    return has_copy_ctor<T>(0); 
} 

DEMO

相關問題