"Si un trabajador quiere hacer bien su trabajo, primero debe afilar sus herramientas." - Confucio, "Las Analectas de Confucio. Lu Linggong"
Página delantera > Programación > Consejos de implementación de captura móvil en C ++ Lambda

Consejos de implementación de captura móvil en C ++ Lambda

Publicado el 2025-04-12
Navegar:681

How to Implement Move Capture in C   Lambdas?

Mover Capture en lambdas

pregunta:

¿Cómo implementamos Mover Capture, también conocido como referencias de RValue, en c 11 lambdas? Por ejemplo:

std::unique_ptr myPointer(new int);

std::function example = [std::move(myPointer)] {
   *myPointer = 4;
};

Respuesta:

Generalized Lambda Capture en C 14

en C 14, captura de lambda generalizada permite la captura de movimiento. Este código ahora es válido:

using namespace std;

auto u = make_unique(some, parameters);  
go.run([u = move(u)] { do_something_with(u); }); 

para mover objetos de una lambda a otra función, haga que la lambda mutable:

go.run([u = move(u)] mutable { do_something_with(std::move(u)); });
[&]

Workaround para mude Capture in Capture in Capture in Capture in Capture in Capture in Capture in Capture in Capture in Capture in Capture in Capture in Capture in Capture in Capture in Capture in Capture in Capture in capture in capture in ctain 11

una función de ayuda, make_rref, puede facilitar la captura de movimiento. Su implementación es la siguiente:

#incluir #Include #Include plantilla struct rref_impl { rref_impl () = delete; rref_impl (t && x): x {std :: movimiento (x)} {} rref_impl (rref_impl & otros) : x {std :: movimiento (other.x)}, iScopied {true} { afirmar (otro.iscopied == falso); } rref_impl (rref_impl && otro) : x {std :: movimiento (otro.x)}, iScopied {std :: Move (OTRO.ISCOPIED)} { } rref_impl & operator = (rref_impl other) = delete; T & operator && () { return std :: mover (x); } privado: T x; bool iscopied = false; }; plantilla rref_impl make_rref (t && x) { return rref_impl {std :: Move (x)}; }
#include 
#include 
#include 

template 
struct rref_impl {
    rref_impl() = delete;
    rref_impl(T&& x) : x{std::move(x)} {}
    rref_impl(rref_impl& other)
        : x{std::move(other.x)}, isCopied{true}
    {
        assert(other.isCopied == false);
    }
    rref_impl(rref_impl&& other)
        : x{std::move(other.x)}, isCopied{std::move(other.isCopied)}
    {
    }
    rref_impl& operator=(rref_impl other) = delete;
    T& operator&&() {
        return std::move(x);
    }

private:
    T x;
    bool isCopied = false;
};

template rref_impl make_rref(T&& x) {
    return rref_impl{std::move(x)};
}
un caso de prueba para make_rref:

int main () { std :: unique_ptr p {new int (0)}; auto rref = make_rref (std :: mude (p)); Auto Lambda = [rref] () mutable -> std :: unique_ptr {return rref.move (); }; afirmar (lambda ()); afirmar (! lambda ()); }
#include 
#include 
#include 

template 
struct rref_impl {
    rref_impl() = delete;
    rref_impl(T&& x) : x{std::move(x)} {}
    rref_impl(rref_impl& other)
        : x{std::move(other.x)}, isCopied{true}
    {
        assert(other.isCopied == false);
    }
    rref_impl(rref_impl&& other)
        : x{std::move(other.x)}, isCopied{std::move(other.isCopied)}
    {
    }
    rref_impl& operator=(rref_impl other) = delete;
    T& operator&&() {
        return std::move(x);
    }

private:
    T x;
    bool isCopied = false;
};

template rref_impl make_rref(T&& x) {
    return rref_impl{std::move(x)};
}

emulando la captura de lambda generalizada en c 11

Otra vigilancia es proporcionada por la función capture ():

#include #Include int main () { std :: unique_ptr p {new int (0)}; auto lambda = captura (std :: movimiento (p), [] (std :: unique_ptr & p) {return std :: Move (p); }); afirmar (lambda ()); afirmar (! lambda ()); }
#include 
#include 
#include 

template 
struct rref_impl {
    rref_impl() = delete;
    rref_impl(T&& x) : x{std::move(x)} {}
    rref_impl(rref_impl& other)
        : x{std::move(other.x)}, isCopied{true}
    {
        assert(other.isCopied == false);
    }
    rref_impl(rref_impl&& other)
        : x{std::move(other.x)}, isCopied{std::move(other.isCopied)}
    {
    }
    rref_impl& operator=(rref_impl other) = delete;
    T& operator&&() {
        return std::move(x);
    }

private:
    T x;
    bool isCopied = false;
};

template rref_impl make_rref(T&& x) {
    return rref_impl{std::move(x)};
}
captura se implementa de la siguiente manera:

#include plantilla clase Capture_impl { T x; F f; público: capture_impl (t && x, f && f) : x {std :: hacia adelante (x)}, f {std :: hacia adelante (f)} {} Template operador automático () (ts && ... args) -> decltype (f (x, std :: hacia adelante (args) ...)) { return f (x, std :: hacia adelante (args) ...); } plantilla operador automático () (ts && ... args) const -> decltype (f (x, std :: hacia adelante (args) ...)) { return f (x, std :: hacia adelante (args) ...); } }; plantilla captura_impl captura (t && x, f && f) { return capture_impl ( std :: hacia adelante (x), std :: hacia adelante (f)); }
#include 
#include 
#include 

template 
struct rref_impl {
    rref_impl() = delete;
    rref_impl(T&& x) : x{std::move(x)} {}
    rref_impl(rref_impl& other)
        : x{std::move(other.x)}, isCopied{true}
    {
        assert(other.isCopied == false);
    }
    rref_impl(rref_impl&& other)
        : x{std::move(other.x)}, isCopied{std::move(other.isCopied)}
    {
    }
    rref_impl& operator=(rref_impl other) = delete;
    T& operator&&() {
        return std::move(x);
    }

private:
    T x;
    bool isCopied = false;
};

template rref_impl make_rref(T&& x) {
    return rref_impl{std::move(x)};
}
Esta solución evita copiar el lambda si el tipo capturado no es copiado, evitando los errores de tiempo de ejecución.

Último tutorial Más>

Descargo de responsabilidad: Todos los recursos proporcionados provienen en parte de Internet. Si existe alguna infracción de sus derechos de autor u otros derechos e intereses, explique los motivos detallados y proporcione pruebas de los derechos de autor o derechos e intereses y luego envíelos al correo electrónico: [email protected]. Lo manejaremos por usted lo antes posible.

Copyright© 2022 湘ICP备2022001581号-3