Сохранение указателя путем продления жизни захвата
Можно ли продлить жизнь unique_ptr
захватывая его в лямбду и продлевая жизнь лямбды?
Я пытался, но получая синтаксические ошибки с a=move(a)
выражение.
#include <cstdio>
#include <functional>
#include <memory>
#include <iostream>
using namespace std;
struct A {
A() { cout << "A()" << endl; }
~A() { cout << "~A()" << endl; }
};
int main() {
std::function<void ()> f;
{
std::unique_ptr<A> a(new A());
f = [a=move(a)] () mutable { return; };
}
return 0;
}
1 ответ
Ну, проблема с вашим кодом std::function
, Он не очень удобен для перемещения, так как требует, чтобы его вызывали, чтобы он был копируемым / присваиваемым, чего нет у вашей лямбды из-за использования только типа перемещения, unique_ptr
в вашем примере.
Есть много примеров, которые могут предоставить вам дружественную версию std::function
,
Я пришел сюда с быстрой, хакерской и, вероятно, склонной к ошибкам, но "работающей на моей машине" той же версией:
#include <memory>
#include <iostream>
#include <type_traits>
struct A {
A() { std::cout << "A()" << std::endl; }
~A() { std::cout << "~A()" << std::endl; }
};
template <typename Functor>
struct Holder
{
static void call(char* sbo) {
Functor* cb = reinterpret_cast<Functor*>(sbo);
cb->operator()();
}
static void deleter(char* sbo) {
auto impl = reinterpret_cast<Functor*>(sbo);
impl->~Functor();
}
};
template <typename Sign> struct Function;
template <>
struct Function<void()>
{
Function() = default;
~Function() {
deleter_(sbo_);
}
template <typename F>
void operator=(F&& f)
{
using c = typename std::decay<F>::type;
new (sbo_) c(std::forward<F>(f));
call_fn_ = Holder<c>::call;
deleter_ = Holder<c>::deleter;
}
void operator()() {
call_fn_(sbo_);
}
typedef void(*call_ptr_fn)(char*);
call_ptr_fn call_fn_;
call_ptr_fn deleter_;
char sbo_[256] = {0,};
};
int main() {
Function<void()> f;
{
std::unique_ptr<A> a(new A());
f = [a=move(a)] () mutable { return; };
}
std::cout << "Destructor should not be called before this" << std::endl;
return 0;
}
Попробуйте сами: /questions/37374244/vyigruzka-bytearray-s-ispolzovaniem-actionscript-3/37374253#37374253