Fino a C++ 11, i flussi C++ sono implicitamente convertibili in void*
. Il risultato sarà NULL
se lo stream non è in uno stato senza errori e qualcos'altro se lo è. Quindi ifs == NULL
(non dovrebbe funzionare con nullptr
, vedi sotto) troverà e userà quella conversione, e dal momento che il tuo nome file è sbagliato, il confronto produrrà vero.
In C++ 11, questo è stato cambiato per una conversione esplicita per bool
, con false
che indica un errore e true
un buon flusso, perché la conversione void*
permesso codice troppo senza senso, come il tuo esempio. In effetti, un compilatore corrente in modalità C++ 11 o C++ 14 rifiuterà il frammento di codice, live. Poiché il tuo codice è ovviamente almeno C++ 11, il tuo compilatore non è conforme accettandolo.
quelle conversioni consentono e sono destinati per i controlli di errore come questo:
if (!(ifs >> data))
std::cout << "Reading data failed.";
o, analogo a tuo esempio:
std::ifstream ifs ("wrong_filename.txt");
if (!ifs)
std::cout << "Could not open file.";
Fun fatto del giorno: è anche possibile utilizzare questo per pulire in modo pulito su un file, ad esempio:
for (std::string line; std::getline(ifs, line);) {
// Process line
}
fonte
2015-10-17 13:21:07
C'è un sovraccarico del cast per 'void *' IIRC. –
Qualsiasi tipo di classe può scegliere di essere paragonabile a un 'nullptr' definendo una conversione implicita a un tipo di puntatore o sovraccaricando' operator == 'in modo appropriato. –
Assegna un nome al compilatore quando si richiede un "dubbio". –