2013-06-27 18 views
55
ifstream f; 
f.open(fileName); 

if (f.fail()) 
{ 
    // I need error message here, like "File not found" etc. - 
    // the reason of the failure 
} 

Hata iletisi nasıl dizilir?ifstream açık başarısız olduğunda hata iletisi nasıl alınır

+2

[C++ ifstream Hata Denetimi] 'nin olası bir kopyası (http://stackoverflow.com/questions/13446593/c-ifstream-error-checking) –

+1

olası kopyası [Bir C++ akışı açıldığında belirli bir hata durumu alır mısınız? başarısız olur?] (http://stackoverflow.com/questions/303966/can-you-get-a-specific-error-condition-when-ac-stream-open-fails) – arne

+3

@Alex Farber: Elbette. "cerr <<" Hata kodu: "<< strerror (errno); // Sorunun neden alakalı olduğunu gösteren bazı bilgiler alın. –

cevap

42

errno değerini güncellemek başarısız Her sistem çağrısı. her sistem çağrısı küresel errno değerini günceller beri Ancak

cerr << "Error: " << strerror(errno); 

Eğer a ifstream açık gibi bir şey kullanarak başarısız olduğunda

Böylece, ne olduğu hakkında daha fazla bilgiye sahip olabilir başka bir sistem çağrısı, f.open'un çalıştırılması ile errno kullanımı arasında bir hata tetiklerse, çok iş parçacıklı bir uygulamada sorunlar olabilir. POSIX standardıyla sisteminde

:

errno parçacığı yerel olduğu; Bir iş parçacığına ayarlamak, başka bir iş parçacığındaki değerini etkilemez.


Düzenleme (Arne Mertz sayesinde ve yorumlar diğer kişi)

:

e.what()

daha C olması ilk bakışta görünüyordu ++ - Bu uygulamanın deyimsel doğru yolu, ancak dize döndü Bu işlev tarafından uygulama bağımlı ve (en azından G ++ 's libstdC++) bu dizede hata arkasında neden hakkında hiçbir yararlı bilgi vardır ...

+1

' e .what() 'fazla bilgi vermez, cevabımdaki güncellemelere bakın. –

+11

'errno' modern işletim sistemlerinde iş parçacığı yerel depolama kullanır. Bununla birlikte, bir "fstream" fonksiyonunun bir errno meydana geldikten sonra "errno" işlevini yitireceğini garanti etmez. Temel işlevler 'errno'yu hiç kurmayabilir (Linux ya da Win32’daki doğrudan sistem çağrıları). Bu pek çok gerçek dünya uygulamalarında işe yaramıyor. – strcat

+0

MSVC'de, "e.what()" her zaman "iostream akış hatası" mesajını aynı anda yazdırır " – rustyx

21

Sen akışı yetmezliği üzerinde bir istisna icar deneyebilirsiniz:

  • Ben Win7, Embarcadero RAD Studio üzerinde denedim:

    std::ifstream f; 
    //prepare f to throw if failbit gets set 
    std::ios_base::iostate exceptionMask = f.exceptions() | std::ios::failbit; 
    f.exceptions(exceptionMask); 
    
    try { 
        f.open(fileName); 
    } 
    catch (std::ios_base::failure& e) { 
        std::cerr << e.what() << '\n'; 
    } 
    

    e.what() Ancak çok yararlı görünmüyor 2010, "ios_base :: failbit set" değerini verirken strerror(errno), "Böyle bir dosya veya dizin yok" verir. Ubuntu 13.04 üzerinde

  • , gcc 4.7.3 istisna bunu anlatacağım bilmiyorum (sizin için çalışmıyor "basic_ios :: berrak" (arne sayesinde) e.what() ise

diyor o) standardize değil çünkü hata, sadece std::make_error_condition (C++ 11) kullanmayı deneyin:

catch (std::ios_base::failure& e) { 
    if (e.code() == std::make_error_condition(std::io_errc::stream)) 
    std::cerr << "Stream error!\n"; 
    else 
    std::cerr << "Unknown failure opening file.\n"; 
} 
+0

Teşekkürler. Bunu test etmedim çünkü 'strerror (errno)' yorum çalışmalarında yayınlandı ve kullanımı çok kolay. Errno'nun çalışmasından bu yana, "e" nin çalışacağını düşünüyorum. –

+0

Ardından Matthieus yanıtındaki çoklu okuma hakkında annotayonlara bakın. Benim tahminim, e.what() 'ın strerror'un ne olduğunu döndürmesidir. Her ikisi de muhtemelen platforma bağlı olacak. –

+0

@AlexFarber: Arne'ın cevabının benimkinden daha iyi olduğunu düşünüyorum. Çözümüm, sorununuzu çözmenin _C++ - way_'ı değil. Ancak, C++ kütüphanesinin sistem hatalarını 'exception.what()' ile nasıl çağırdığıyla ilgili resmi bir bilgi bulamadım. LibstdC++ kaynak kodu :-) –

13

@ Arne Mertz yanıtı, C++ 11itibariyle, strerror(errno)'un döndüreceği hata kodunu ve iletiyi içeren system_error (bkz. http://www.cplusplus.com/reference/ios/ios_base/failure/) öğesinden devralınır.

std::ifstream f; 

// Set exceptions to be thrown on failure 
f.exceptions(std::ifstream::failbit | std::ifstream::badbit); 

try { 
    f.open(fileName); 
} catch (std::system_error& e) { 
    std::cerr << e.code().message() << std::endl; 
} 

Bu No such file or directory.fileName eğer yoksa yazdırır.

+5

MSVC 2015'te" iostream stream error "i basar. – rustyx

+0

Benim için GCC 6.3 ayrıca iostream hatası 'yazdırır. Hangi derleyiciyi test ettin? Herhangi bir derleyici aslında başarısızlık için kullanıcı tarafından okunabilir bir neden sağlar mı? – Ruslan

İlgili konular