2013-03-27 24 views
7

Ho familiarità con il funzionamento dell'asserzione C++ standard. Questo ha funzionato bene nel mio progetto per una serie di scopi di test.C++ Funzione di asserzione per controllare che venga lanciata un'eccezione

Ad esempio, supponiamo di voler controllare che una determinata eccezione venga generata dal mio codice.

È possibile eseguire questa operazione senza utilizzare un framework di test come CPPUnit?

+0

in base al post: http://stackoverflow.com/questions/37473/how-can-i-assert-without-using-abort. Che ne dici di scrivere una macro che usa '' catch''? – gongzhitaao

risposta

-2

in-codice affermazioni sono di solito utilizzati per l'inizio di un metodo, al fine di confermare che alcune pre-condizioni sono state soddisfatte, prima dell'entrata di questa particolare funzione ad esempio:

Window::paint() 
{ 
    assert(m_device != NULL); 
    m_device->repaintRegion(); 
} 

sono qui principalmente per intercettare gli errori di dipendenze non soddisfatte tra metodi o classi.

le asserzioni nei framework di test sono diverse e solitamente utilizzate per il test dell'unità, per assicurarsi che l'unità abbia restituito tutto ciò di cui aveva bisogno per tornare.

Le eccezioni dovrebbero essere generate in genere laddove la realtà (cioè i sistemi esterni) ci ha fornito un caso che il codice non può/non deve gestire. è una via facile per problemi rari ma ancora attesi. per esempio - un timeout in attesa di un server solitamente disponibile. o, non abbastanza memoria. Non lo userei come aiuto per la logica di programmazione.

alla tua domanda, potrebbe esserci un modo per cogliere le eccezioni nei framework di test circondando l'unità testata con try-catch. ma non sono sicuro che sia davvero desiderabile.

HTH

+1

Non vedo come questo possa aiutare. –

2

uno scheletro (non testato)

#define MY_ASSERT(f, e) {\ 
    try {\ 
     f();\ 
    } catch (std::exception &e) {\ 
     ...\ 
    }\ 
} 
6

È possibile fare la stessa cosa CPPUnit does manualmente:

bool exceptionThrown = false; 

try 
{ 
    // your code 
} 
catch(ExceptionType&) // special exception type 
{ 
    exceptionThrown = true; 
} 
catch(...) // or any exception at all 
{ 
    exceptionThrown = true; 
} 

assert(exceptionThrown); // or whatever else you want to do 

Naturalmente, se si utilizza questo modello molto, ha senso usare una macro per questo.

0

Ecco un tester di eccezione che ho scritto in base alle risposte di @JPlatte e @ gongzhitaao. Per il mio framework di test ho due variabili globali num_test e num_test_success che tracciano quanti test sono eseguiti e quanti hanno successo su una serie di test, ma questo può essere modificato in base alle proprie esigenze.

int num_test; 
int num_test_success; 

#define UT_ASSERT_THROW(expression, ExceptionType) {   \ 
                   \ 
    try {              \ 
     expression;            \ 
     printf("test %d: *** FAILURE ***  %s:%d:%s,%s\n", \ 
       num_test, __FILE__, __LINE__,     \ 
       #expression, #ExceptionType);     \         
    } catch (const ExceptionType &) {       \ 
     printf("test %d: success\n", num_test);    \ 
     ++num_test_success;          \ 
    } catch (...) {            \ 
     printf("test %d: *** FAILURE ***  %s:%d:%s,%s\n", \ 
       num_test, __FILE__, __LINE__,     \ 
       #expression, #ExceptionType);     \ 
    }               \ 
                   \ 
    ++num_test;             \ 
                   \ 
} 

Le macro __FILE__ e __LINE__ espandono al file corrente e numero di linea (vedi https://gcc.gnu.org/onlinedocs/cpp/Standard-Predefined-Macros.html). I segni di cancelletto all'interno della macro indicano al preprocessore di posizionare l'argomento come una stringa nell'espansione macro (vedere http://bruceblinn.com/linuxinfo/Stringification.html).

Problemi correlati