Comment vérifier si std::function est vide en C++11?
Je me demandais comment bien vérifier si une std::function
est vide. Considérons cet exemple:
class Test {
std::function<void(int a)> eventFunc;
void registerEvent(std::function<void(int a)> e) {
eventFunc = e;
}
void doSomething() {
...
eventFunc(42);
}
};
Ce code se compile très bien dans MSVC mais si je l'appelle doSomething()
sans l'initialisation de la eventFunc
le code évidemment se bloque. C'est prévu, mais je me demandais quelle est la valeur de la eventFunc
? Le débogueur dit 'empty'
. J'ai donc résolu à l'aide de simples si la déclaration:
void doSomething() {
...
if (eventFunc) {
eventFunc(42);
}
}
Cela fonctionne, mais je me demande encore quelle est la valeur de la non-initialisé std::function
? Je voudrais écrire if (eventFunc != nullptr)
mais std::function
est (évidemment) pas un pointeur.
Pourquoi la pure si les œuvres? Quelle est la magie derrière tout cela? Et, est-ce la bonne façon de le vérifier?
- Notez que
eventFunc
n'est pas un lambda, c'est unstd::function
. Vous pouvez stocker des lambdas dansstd::function
s, mais ils ne sont pas la même chose. - Vous avez raison, j'ai changé le titre pour éviter toute confusion. Merci.
Vous devez vous connecter pour publier un commentaire.
Vous n'êtes pas vérifiant qu'un vide lambda, mais si le
std::function
a un callable cible est stockée. La case est bien définie et fonctionne en raison destd::fonction: fonction:opérateur booléen
qui permet la conversion implicite enbool
dans des contextes où les valeurs booléennes sont nécessaires (telles que l'expression conditionnelle dans unif
déclaration).En outre, la notion de vide lambda n'a pas vraiment de sens. Derrière les coulisses, le compilateur convertit une expression lambda dans un
struct
(ouclass
) de la définition, avec les variables de la capture des données enregistrées par les membres de cestruct
. Une fonction publique à l'appel de l'opérateur est également définie, qui est ce qui permet d'invoquer le lambda. Donc, ce serait un vide lambda être?Vous pouvez également écrire
if(eventFunc != nullptr)
si vous le souhaitez, il est équivalent au code que vous avez dans la question.std::function
définitoperator==
etoperator!=
surcharges pour les comparant avec unnullptr_t
.== nullptr
faire la même chose, si? Il semble qu'il y est censé être une surcharge pour le==
opérateur qui provoque un "vide",std::function
de comparertrue
contrenullptr
: cplusplus.com/reference/functional/function/operatorsnullptr
sera trop de travail,if(eventFunc != nullptr)
est équivalent àif(eventFunc)
dans la question ci-dessus.std::function::operator bool
ne permet pas de conversion implicite enbool
. Il est marquéexplicit
après tout, mais la série fait une exception pour certaines constructions de langage que s'attendre à des expressions booléennes, en l'appelant "contextuellement converti bool." Vous pouvez trouver le fragment de standardese et une explication ici: chris-sharpe.blogspot.com/2013/07/...explicit
, c'est pourquoi j'ai fait très attention à l'état de permet la conversion implicite debool
dans des contextes où les valeurs booléennes sont requis. C'est exactement ce qui se passe dans le code en question.Vérifier ici http://www.cplusplus.com/reference/functional/function/operator_bool/
Exemple
Sortie
swap()
. Je pensais que la sortie était en arrière jusqu'à ce que j'ai réalisé il.