Strange behavior with std :: function

I use the standard shell functions from the C ++ 11 library, and I see strange behavior with its logical operator. If I create an object std::function, the boolean operator returns false. This is true if I assign an nullptrobject to an object and validate it again. The problem occurs when I assign her a void pointer, which I entered in the function pointer. Consider the following program:

#include <functional>
#include <iostream>

void* Test() {
    return nullptr;
}

int main(int argc, char* argv[]) {
    std::function<void()> foo;
    std::cout << !!foo << std::endl;

    foo = nullptr;
    std::cout << !!foo << std::endl;

    foo = reinterpret_cast<void(*)()>(Test());
    std::cout << !!foo << std::endl;

    return 0;
}

What I expect as output 0 0 0, but the result 0 0 1(see demo ). Can someone explain why the boolean operator returns true when it contains a pointer to a null, non-invoked function? And please also mention the workaround for checking nullptrinstd::function

. , ( foo.target<void*>() == nullptr) , , , , ( ).

+4
2

. -, , :

#include <functional>
#include <iostream>

typedef void (*VF)();

VF Test() {
    return nullptr;
}

int main(int argc, char* argv[]) {
    std::function<void()> foo(Test());
    std::cout << !!foo << std::endl;
    return 0;
}

- 1 GCC. :

20.8.11.2.1
template<class F> function(F f);
template <class F, class A> function(allocator_arg_t, const A& a, F f);
7 : F CopyConstructible. F Callable (20.8.11.2) ArgTypes R. A .
8 : !*this :

  • F NULL.
  • F NULL .
  • F - , !f
+5

, , . :

foo = reinterpret_cast<void(*)()>(Test());

, void* Test(). reinterpret_cast - . , undefined, .

5.2.10 [expr.reinterpret.cast]

8 . , , , , dierent cv-qualification, .

9 (4.10) . [: std::nullptr_t , . - ]

4.10 [conv.ptr]

1 (5.19) prvalue , 0 std::nullptr_t. ; .

( )

, std::function ( ) :

#include <iostream>

int main() {
    using fp_t = void(*)();
    void* vn = nullptr;
    fp_t foo = reinterpret_cast<fp_t>(vn); // GCC: warning, Clang: silence
    //fp_t foo = reinterpret_cast<fp_t>(nullptr); // error (GCC and Clang!)
    std::cout << !!foo << std::endl;
}

+4

All Articles