[英]`enable_if()` to disable static member function declaration of templated class
我正在嘗試在模板 class 中聲明 function ,以便 function 聲明取決於模板類型參數。
template<typename T>
struct Block
{
static bool parse(int32_t index,
const typename std::enable_if<std::is_class<T>::value, T>::type& value);
static bool parse(int32_t index,
typename std::enable_if<!std::is_class<T>::value, T>::type value);
....
};
所以我想擁有Block<uint16_t>
和Block<std::string>
和parse()
聲明為:
bool parse(int32_t index, const std::string& value);
or
bool parse(int32_t index, uint16_t value);
但我收到錯誤: 'enable_if' cannot be used to disable this declaration...typename std::enable_if<:std::is_class<T>:,value: T>:;type value);
你能幫我正確聲明函數嗎?
謝謝。
Enable_if 僅適用於推斷的上下文。 在您的示例中,扣除是在 class 類型時間完成的。 當你得到函數的時候,T 已經知道了,所以沒有什么可以推導出來的。
您可以制作一個多余的模板參數,將其默認類型設置為 T 然后推斷。
template<typename T>
struct Block
{
// now parse has to deduce U
template<typename U=T>
static bool parse(int32_t index,
typename std::enable_if<!std::is_class<U>::value, T>::type value);
你的調用者永遠不會知道parse
實際上有一個模板參數,但現在你可以在它上面做所有花哨的事情。
沒有 SFINAE 的替代解決方案是使用標簽調度:
template<typename S> static bool parse(int32_t index, S&& value) { return parse_impl(index, value, std::is_class<T>{}); } private: static bool parse_impl(int32_t index, const T& value, std::true_type); static bool parse_impl(int32_t index, T value, std::false_type);
請注意,在此解決方案中, parse()
接受任何類型S
,如果S
不能轉換為T
,則失敗將發生在parse()
本身內部。 如果parse()
本身用於 SFINAE,這可能為時已晚。 例如,以下模板:
template<class S, class T, typename = decltype(S::parse(0, std::declval<T>()))>
將導致原始parse()
的軟失敗(這不是錯誤)和建議的標記分派版本的硬失敗(這是一個編譯錯誤)。 感謝xaxxon指出這種差異。
在帶有概念的 C++20 中, requires
將簡化事情:
static bool parse(int32_t index, const T& value) requires std::is_class_v<T> {... } static bool parse(int32_t index, T value) requires:std:.is_class_v<T> {... }
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.