如何转发声明依赖于变量定义的类,而变体定义又依赖于模板化类?

How to Forward Declare a Class that Relies on a Variant Definition, Which In Turn Relies on a Templated Class?

本文关键字:定义 依赖于 何转发 转发 变量 声明      更新时间:2023-10-16

我有一个名为Foo的类。我还有一个名为Fum的模板化类。Fum<Foo>包含类型为Foo的数据成员。此外,我有一个变体定义typedef std::variant< Fum<Foo> /* etc.*/ > var_t;.Foo包含类型var_t的数据成员。

如您所见,var_t取决于FumFoo,而Foo取决于var_t。我可以执行哪些声明序列来编译以下代码:

阅读错误注释

尝试 1:

#include <iostream>
#include <variant>   
// Forward Decls
template <typename T>
class Fum;
class Foo;

typedef std::variant< Fum<Foo> /* etc.*/ > var_t;
template<typename T>
class Fum {
private:
// Error: Incomplete type Foo.
T value;
public:
/*
+++++ Construct T object emplace +++++
*/
template<typename ... Params>
Fum<T>(Params&& ... argsOfT)
:value(std::forward<Params>(argsOfT)...)
{}
Fum<T>(Fum<T>&& fumObj)
:value(std::move(fumObj.value))
{}
}; // Fum

class Foo {
private:
var_t val;

public:

Foo(var_t&& valParam)
:val(std::move(valParam))
{}
}; // Foo

尝试 2:

#include <iostream>
#include <variant> 
// Forward Decls
template <typename T>
class Fum; // note: template is declared here
class Foo;

typedef std::variant< Fum<Foo> /* etc.*/ > var_t;

class Foo {
private:
var_t val;

public:

Foo(var_t&& valParam)
:val(std::move(valParam))
{}
}; // Foo
template<typename T>
class Fum {
private:
//  note: in instantiation of template class 
// 'std::__1::variant<Fum<Foo> >' requested here
T value;
public:
/*
+++++ Construct T object emplace +++++
*/
template<typename ... Params>
Fum<T>(Params&& ... argsOfT)
:value(std::forward<Params>(argsOfT)...)
{}
Fum<T>(Fum<T>&& fumObj)
:value(std::move(fumObj.value))
{}
}; // Fum

我认为你不能。

多属性的备选方案必须全部为完整类型,并且您的Fum<T>T存储为成员。

几个月前我遇到了类似的问题。我有这样的设计,其中一个替代方案是vector<T>,这很好,因为即使T不是,vector<T>也是完整的......但我不相信你的Fum<T>是这种情况,当我开始尝试其他一些容器时,情况并非如此。

如果Fum而是存储一些指针,并动态分配其T,那就没问题了。

不可能,因为您有一个没有间接寻址(指针或引用(的循环定义。 因此,所有对象都直接相互包含,最终要求

sizeof(var_t) > sizeof(Fum<Foo>) >= sizeof(Foo) >= sizeof(var_t)

这是不可能的。