2013-03-02 115 views
7

當C++ 11不可用時,應該使用什麼構造作爲std::function<>的代理?
替代方案應該基本上允許從下面的例子中訪問另一個類的一個類的私有成員函數(不使用std :: function的其他功能)。 Foo類是固定的,不能改變太多,我只能訪問類Bar。在C++ 11之前是否有類似於std :: function的東西?

class Foo { 
    friend class Bar; // added by me, rest of the class is fixed 
    private: 

    void doStuffFooA(int i); 
    void doStuffFooB(int i); 
}; 

class Bar { 
    public: 

    Bar(Foo foo, std::function< void (const Foo&, int) > func) { 
    myFoo = foo; 
    myFooFunc = func; 
    }; 

    private: 

    doStuffBar(const &Foo foo) { 
    myFooFunc(foo, 3); 
    } 

    Foo myFoo; 
    std::function< void (const Foo&, int) > myFooFunc; 
} 

int main() { 

    Foo foo(...); 

    Bar barA(foo, &Foo::doStuffFooA); 

    Bar barB(foo, &Foo::doStuffFooB); 
    ... 
} 
+1

這個代碼不被編譯,即使明顯語法錯誤是固定的。這兩個'Bar'對象是用指向私有成員函數的指針構造的,但是發生這種情況的代碼無法訪問這些成員。這與'std :: function'無關;它不會破壞訪問規則。 – 2013-03-02 17:37:24

回答

10

是否有類似的std之前C++ 11 ::功能的東西嗎?

。有Boost.Function(boost::function<>),最近成爲C++標準庫的一部分,並提供了std::function<>的參考實現;同樣,標準採用了Boost.Bind(boost::bind<>()),併成爲std::bind<>()

它實現了一種稱爲類型擦除用於保存任何類型的可調用對象。以下是可能的,說明性實施的怎麼這麼類模板可以從頭來定義(不要在生產代碼中使用,這僅僅是一個例子):

#include <memory> 

template<typename T> 
struct fxn { }; 

template<typename R, typename... Args> 
struct fxn<R(Args...)> 
{ 

public: 

    template<typename F> 
    fxn(F&& f) 
     : 
     _holder(new holder<typename std::decay<F>::type>(std::forward<F>(f))) 
    { } 

    R operator() (Args&&... args) 
    { _holder->call(std::forward<Args>(args)...); } 

private: 

    struct holder_base 
    { virtual R call(Args&&... args) = 0; }; 

    template<typename F> 
    struct holder : holder_base 
    { 
     holder(F&& f) : _f(std::forward<F>(f)) { } 
     R call(Args&&... args) { return _f(std::forward<Args>(args)...); } 
     F _f; 
    }; 

    std::unique_ptr<holder_base> _holder; 
}; 

#include <iostream> 

int main() 
{ 
    fxn<void()> f = [] { std::cout << "hello"; }; 
    f(); 
} 
+0

事實上,來自助推的許多功能可以被視爲「預標準」。 – leemes 2013-03-02 14:49:37

+0

不錯的代碼表明我們可以從頭開始構建這個代碼,但是您必須記住這是C++ 11。 ;)我猜boost實現要複雜得多(我猜他們使用它的預處理器庫?) – leemes 2013-03-02 14:53:49

+0

@leemes:當然可以。我只是想或多或少提供實施原則的見解。這不僅僅是C++ 11,也是非常基礎的。 – 2013-03-02 14:57:03

相關問題