Clang无法在模板类专门化中编译模板函数,该模板类具有从模板声明的* distinct返回类型* [英] Clang fails to compile template function in a template class specialization, which has *distinct return type* from the template declaration

查看:298
本文介绍了Clang无法在模板类专门化中编译模板函数,该模板类具有从模板声明的* distinct返回类型*的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

以下函数 derefItemX()在GCC 4.8-5.3上编译得很好,但在CLang 3.8上失败:

The following function derefItemX() is compiled fine on GCC 4.8-5.3, but fails on CLang 3.8:

//! Accessory Operations - template argument depended wrappers
template<bool SIMPLE>  // For Nodes / non-scoped storage
struct Operations {
    //! \brief Defererence wrapped or direct iterator
    //!
    //! \param iel IItemXT&  - iterator to be dereferenced
    //! \return ItemT&  - resulting reference
    template<typename IItemXT>
    constexpr static auto& derefItemX(IItemXT& iel)
    {
        static_assert(is_base_of<std::forward_iterator_tag, typename IItemXT::iterator_category>::value
            , "derefItemX(), IItemXT must be a forward iterator type");
        return **iel;  // Dereference an iterator of pointer to the value
    }
};

//! Specialization for non-scoped storage (direct pointers)
template<>
template<typename IItemXT>
constexpr auto& Operations<true>::derefItemX(IItemXT& iel)
{
    static_assert(is_base_of<std::forward_iterator_tag, typename IItemXT::iterator_category>::value
        , "derefItemX(), IItemXT must be a forward iterator type");
    return *iel;  // Dereference an iterator of value to the value
}


...
// Usage:
auto& el = Operations<!is_pointer<typename IItemXT::value_type>
            ::value>::derefItemX(ic);

derefItemX()值或指向值的指针指向原始值。 CLang显示以下错误消息:
说不多:

derefItemX() dereferences an iterator of either a value or a pointer to the value to original value. CLang shows the following error message: that says not much:

include/hierarchy.hpp:168:35: error: out-of-line definition of 'derefItemX' does not match any declaration in 'XXX::Operations<true>'
constexpr auto& Operations<true>::derefItemX(IItemXT& iel)
                                  ^~~~~~~~~~

任何人请解释:


  1. 为什么CLang无法编译 derefItemX c $ c>?

  2. 如何使用另一种方法将迭代器参数化为* x或** x,可用于不同的编译器?



    非常感谢!

Thanks a lot!

注意

在模板声明和特化中指定返回类型但是不同时,C ++ 11存在问题。

看起来像CLang要求匹配模板函数的返回类型在模板类声明和专门化中),它们不是根据标准的函数签名的一部分。 @ max66指定的交叉编译器解决方案是具有模板类的空声明和所需的特殊化。

Note:
The same problem exists for C++11 when the return type is specified, but differs in the template declaration and specialization.
Looks like CLang requires to match the return types (of template functions in the template class declaration and specialization), which are not part of the function signature according to the standard. The "cross-compiler" solution as specified by @max66 is to have an empty declaration of the template class and required specializations.

推荐答案

我不怎么解决问题的一般方式;但这个问题(如果我没有错)可以解决专门整个类;像

I don't how to solve the problem in a general way; but this problem (if I'm not wrong) could be solved specializing the entire class; something like

#include <iterator>
#include <type_traits>

using namespace std;

template <bool>
struct Operations;

template<>
struct Operations<false> {
   template<typename IItemXT>
      constexpr static auto& derefItemX(IItemXT& iel)
       {
         static_assert(is_base_of<std::forward_iterator_tag, typename IItemXT::iterator_category>::value
                       , "derefItemX(), IItemXT must be a forward iterator type");
         return **iel;  // Dereference an iterator of pointer to the value
       }
};

template<>
struct Operations<true> {
   template<typename IItemXT>
      constexpr auto& derefItemX(IItemXT& iel)
       {
         static_assert(is_base_of<std::forward_iterator_tag, typename IItemXT::iterator_category>::value
                       , "derefItemX(), IItemXT must be a forward iterator type");
         return *iel;  // Dereference an iterator of value to the value
       }
};

关于为什么clang无法编译的问题...我很困惑,不知道谁在g ++和clang ++之间。

Regarding the problem "why the clang fail to compile"... i'm confused and I don't know whos right between g++ and clang++

ps:对不起我的英语

p.s.: sorry for my bad English

这篇关于Clang无法在模板类专门化中编译模板函数,该模板类具有从模板声明的* distinct返回类型*的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆