std :: any用于无法复制构造的对象

时间:2017-10-20 15:14:38

标签: c++ templates c++17 template-meta-programming

我有一个包含unique_ptr的对象,因此无需进行复制而无需进行深层复制(我不想要)。

我想让std :: any持有该对象,但我发现的唯一选择是让std :: any持有一个指针,这会增加一个无用的间接,或者让我的对象有一个独特的ptr。下面的代码有望说明我的观点:

//Compiled with clang++ -std=c++2a; clang version 5.0.0
#include <iostream>
#include <any>
#include <memory>

struct A {
        std::unique_ptr<int> m = std::make_unique<int>(11);
        A(A&& a): m(std::move(a.m)) {}
        A() {}
};

struct B {
        std::shared_ptr<int> m = std::make_shared<int>(11);
};


template<class T>
void use_any_ptr() {
        std::any a{new T{}};
        std::cout << *(std::any_cast<T*>(a)->m) << std::endl;
}

template<class T>
void use_any() {
        std::any a{T{}};
        std::cout << *(std::any_cast<T>(a).m) << std::endl;
}


int main() {
        use_any_ptr<A>(); // Workaround using a pointer
        use_any<B>(); // Workaround using shared pointer
        use_any<A>(); // Breaks because A has no cc no matching constructor for initialization of 'std::any'
}

据我所知,std :: any的构造似乎需要复制对象,但我不确定为什么不能简单地移动对象。

有办法解决这个问题吗?也就是说,除了使用shared_ptr之外,这意味着我基本上表达了错误的东西&#34;为了创建任何对象或传递std :: any指针(这是一个不需要的间接层,因为std :: any包含一个指向该类型的void指针,据我所知)。

是否有任何可以在创建时使用move ctr而不是copy ctr的实现?

或者我是愚蠢而不理解&#34;真实&#34;问题在这里?

1 个答案:

答案 0 :(得分:3)

  

或者我是愚蠢而不理解&#34;真实&#34;问题在这里?

问题在这里很简单:std::anya copy constructor,因此它要求包含的对象是可复制的。

你可以解决它的方法是定义一个包含指针的自定义对象,该指针是可复制的,并为它实现正确的逻辑(无论正确意味着什么)在你的情况下,我无法看到你如何复制std::any,因此包含那里拥有std::unique_ptr的对象,但也许你可以在某种情况下以某种方式逃脱它。

否则重新考虑您的设计并尝试摆脱std::any的需要。它确实没有太多用途,可能你可以使用一些模板机器或std::variant或其他

来获得相同的功能。