我正在尝试获取一个cmake C ++项目,该项目可以编译并与GCC一起运行以与MSVC一起编译。我正在使用VS2017。
我不是我要负责使其与MSVC一起编译的代码的作者。
该项目很大,所以我不确定如何展示MCVE。但是,我将尽力在这里尽力解释:
我收到此错误:
对应于下面的friend
类中的sibling_iterator
声明。
但是,leftmost_output()
是node
的成员。
node
的定义附在下面(参见向下的3/4):
我很确定这是related to the bug in VS related to nested template classes,因为sibling_iterator
和node
嵌套在另一个模板类中。
我的问题是如何使整个节点类成为朋友,而不是指定特定的成员函数?这样做可能会失败,除非有其他建议值得欢迎。
答案 0 :(得分:1)
最小的可复制代码是:
#include <map>
template <class T, class T2>
struct relative_iterator : T {};
struct edge : public std::map<int, int>::iterator {};
using T_edge = edge;
class node {
public:
template <class T_iterable, class T_content>
class sibling_iterator : public relative_iterator<T_iterable, T_content>
{
public:
friend sibling_iterator<edge, T_edge> node::leftmost_output();
//..
};
static sibling_iterator<edge, T_edge> leftmost_output(); // <--move up
} ;
有两种解决方法:
将leftmost_output()
上的class sibling_iterator
的定义移到
使node
为从属名称。如果name
有一个依赖于T_iterable
的别名,则其查找将延迟到实例化class sibling_iterator<T_iterable, T_contents>
的时间。最简单的方法是在标准中使用标准实用程序:
class sibling_iterator : public relative_iterator<T_iterable, T_content>
{
public:
static constexpr bool dependent_true = std::is_same<T_iterable,T_iterable>::value;
using dependent_node = typename std::enable_if<dependent_true, node>::type;
friend sibling_iterator<edge, T_edge> dependent_node::leftmost_output();
};
但是,如果您想定义自己的解决方案,则可以定义dependet_type<T, Dependent>
助手:
template <class T, class Dependent>
struct dependent_type
{
using type = T;
};
template <class T, class Dependent>
using dependent_type_t = typename dependent_type<T, Dependent>::type;
并使用它:
template <class T_iterable, class T_content>
class sibling_iterator : public relative_iterator<T_iterable, T_content>
{
public:
using dependent_node = typename dependent_type<node, T_iterable>::type;
friend sibling_iterator<edge, T_edge> dependent_node::leftmost_output();
//..
};
我认为这是最好的选择,因为它需要对现有代码库进行较少的更改。
我会写一个简短的变体:
friend sibling_iterator<edge, T_edge> dependent_type_t<node, T_iterable>::leftmost_output()
这看起来很完美,因为它需要对源代码进行最少的更改。如果没有使编译器崩溃,我会写的:
fatal error C1001: An internal error has occurred in the compiler.
(compiler file 'msc1.cpp', line 1469)
答案 1 :(得分:0)
我收到此错误:
错误C2039:'leftmost_output':不是'mv :: graph :: node'的成员
[...]
但是,leftmost_output()是节点的成员。
节点的定义附在下面(参见方法的3/4) 下):
很明显,VC编译器找不到node
的定义,因为它所指的是不同范围的东西。尝试将朋友声明移到嵌套node
类的定义下方。