C++ 實現簡單的閉包

這裏的閉包指的是一個閉包類,這個閉包類使用一個通用的輔助接口函數(如 NewCallback)來生成。在生成的時候傳入須要使用的函數指針以及這個函數將要使用到的參數,生成閉包工具類後再使用一個經過的輔組函數(如 Run)讓函數指針執行。閉包將函數和參數封裝到類中,在必定的場景下進行使用,這就是閉包的做用。html

示例

#include <iostream>
#include <string>

class Closure {
public:
    Closure() {}
    ~Closure() {}

    virtual void Run() = 0; //純虛函數
};

template <typename Arg1>
class FunctionClosure1 : public Closure {
public:
    typedef void (*FunctionType)(Arg1);

    FunctionClosure1(FunctionType f, Arg1 arg1) :
        _f(f),
        _arg1(arg1) {
        }
    ~FunctionClosure1() {
    }

    virtual void Run() {
        _f(_arg1);
        delete this;
    }
private:
    FunctionType _f;
    Arg1 _arg1;
};

template <typename Arg1>
Closure* NewCallback(void(*function)(Arg1), Arg1 arg1) {
    return new FunctionClosure1<Arg1>(function, arg1);
}

// 帶一個參數的函數
template<typename type>
void foo(type data) 
{
    std::cout << "foo data=" << data << std::endl;
}

int main()
{
    Closure* closure;
    closure = NewCallback(foo<std::string>, std::string("titus"));
    //等價於 closure = new FunctionClosure1<std::string>(foo<std::string>, std::string("titus"));
    closure->Run();
    //本身釋放 delete closure
    return 0;
}

Closure 定義爲純虛類,不能實例化,必須由子類實現它的虛函數後再才能實例化。ios

FunctionClosure1 爲 Closure 的子類,定義爲模版類,能夠定製傳入參數的類型。它有兩個私有成員,函數指針成員 _f,參數 _arg1,在成員方法 Run 中會讓函數 _f 傳入參數 _arg1 進行調用。而函數指針成員是在類初始化時傳入的,至關於函數也是能夠定製的。運行完以後 delete this,這是由於 NewCallback 在堆上 new 了一個對象,這裏自動進行資源釋放,固然也能夠本身釋放。git

NewCallback 是一個輔助函數,用來生成子閉包類,它須要傳入函數指針和參數。github

在使用時,父指針指向 NewCallback建立的子類,同時傳入函數指針和參數,最後調用子類繼承實現的 Run 方法。閉包

這麼看來,閉包能夠當作是對回調函數的封裝。函數

標準庫寫法

頭文件引入 functional 標準庫,用 C++11 的寫法也能夠實現上述例子工具

std::function<void(string)> std_closure=foo;
std_closure(string("test std"));

使用 lambda 表達式this

std::function<void()> std_closure = []() {foo(string("test lambda"));};
std_closure();

參考

http://www.cnblogs.com/Aion/p/3449756.html指針

http://yingshin.github.io/c/cpp/2015/12/01/closure-implement-in-C++code

http://www.cnblogs.com/lvpengms/archive/2011/02/21/1960078.html

相關文章
相關標籤/搜索