Разница между std:: function и стандартным указателем функции? [дубликат]


этот вопрос уже есть ответ здесь:

в чем разница между std::function и стандартным указателем функции?

что есть:

typedef std::function<int(int)> FUNCTION;
typedef int (*fn)(int);

действительно ли это одно и то же?

4 53

4 ответа:

указатель на функцию-это адрес фактической функции, определенной в C++. Ан std::function - это оболочка, которая может содержать любой тип вызываемого объекта (Объекты, которые могут использоваться как функции).

struct FooFunctor
{
    void operator()(int i) {
        std::cout << i;
    }
};

// Since `FooFunctor` defines `operator()`, it can be used as a function
FooFunctor func;
std::function<void (int)> f(func);

здесь std::function позволяет абстрагироваться от того, с каким именно вызываемым объектом Вы имеете дело-вы не знаете, что это FooFunctor, вы просто знаете, что он возвращает void и один

они совсем не одинаковы. std::function - это сложный, тяжелый, статусный, почти магический тип, который может содержать любую вызываемую сущность, в то время как указатель функции на самом деле является простым указателем. Если вам это сойдет с рук, вы должны предпочесть либо голые указатели функций, либо auto -bind/auto-лямбда-типов. Используйте только std::function Если вам действительно нужен систематический способ организации гетерогенной коллекции вызываемых сущностей, таких как функции, функторы, захват лямбд и привязка выражения.


обновление: немного объяснений о auto типы: сравните следующие две функции:

void do_something_1(std::function<void(int)> f, int a) { f(a); }

template <typename F, typename A> void do_something_2(F f, A a) { f(a); }

теперь представьте, что вы вызываете их с помощью лямбды или bind выражение:

do_something_X([foo, &bar](int n){ bar += n*foo; },     12);
do_something_X(std::bind(X::bob, &jim, true, _1, Blue), 13);

вторая версия с шаблоном более эффективна, потому что в обоих случаях аргумент F выводится к фактическому, непознаваемому типу выражения. Первая версия, с std::function, это не является шаблоном и может выглядеть проще и продуманнее, но это всегда форсирует строительство std::function объект, и вполне возможно, несет несколько типов стирания и виртуальных затрат на отправку.

A std::function есть государство. Он может содержать дополнительные параметры, "привязанные" к нему.

эти параметры могут варьироваться от таких вещей, как другие классы, другие функции или даже указатели на вызовы функций-членов.

указатель функции замены не typedef int (*fn)(int);

Это typedef int (*fn)(void*,int); С void* reperensting состояние, которое будет скрыто в std::function.

нет.

один-указатель на функцию; другой-объект, который служит оболочкой вокруг указателя на функцию.

они представляют то же самое, но std::function и далеко более мощный, что позволяет делать привязки и еще много чего.