[Cppunit-devel] CookBook "bug"
Brought to you by:
blep
From: Attila F. F (JO/LMF) <att...@er...> - 2003-12-04 09:55:17
|
http://cppunit.sourceforge.net/doc/1.9.11/cppunit_cookbook.html#cppunit_cookbook 8<=== class ComplexNumberTest : public CppUnit::TestCase { public: ComplexNumberTest( std::string name ) : CppUnit::TestCase( name ) {} void runTest() { CPPUNIT_ASSERT( Complex (10, 1) == Complex (10, 1) ); CPPUNIT_ASSERT( !(Complex (1, 1) == Complex (2, 2)) ); } }; ... class Complex {}; Now create an instance of ComplexNumberTest above, compile the code and see what happens. The first thing we notice is a few compiler errors. The test uses operator==, but it is not defined. Let's fix that. bool operator==( const Complex &a, const Complex &b) { return true; } Now compile the test, and run it. This time it compiles but the test fails. ... ===>8 This is unfortunately not true. The Complex class above only has a default constructor. If you look at the ComplexNumberTest you will see that it tries to use a constructor taking two numeric arguments - so it will still not compile. The rest of this mail is rather a rumination-ran-wild... This brings us to the other topic - first tests should aim at the code being compilable, more precisely the classes being "instantiate-able". Then, one can start making more complex tests. And the above hints at another, rather big difference between C++ and Java. In Java most of the errors are runtime. In C++ the code may be wrong because in certain conditions it does not compile. I am not talking about missing functions or functionality. I am talking about (for example) lookup failures. The function is there, but it is not found. Or it is there, it is found - but if I add a header file of another class(es) I want to use together with this one (or standard headers) the call may become ambiguous. That leads to another difference between testing Java and testing C++. And that in some way (possibly) belongs to this fixture part. In Java I can mostly decide runtime of how to create an object. I can select which constructor to call (eg: even from a test script) and then call it with some arguments. Tada, I have an object. But in C++ we have templates! And that might cause some headache, since some of their "arguments" are actually fixed at runtime. Where does this all point? I guess what the hint is that tests should possibly not be described by C++ code but rather some sort of external scripting language, which will then be used to generate the test cases - automatic or interactive. The drawback is that it is a lot of work. The positive is that if it is possible to define this scripting language high-level-enough, it can be used to generate tests for *any* language, not only C++. Of course some test cases might be language specific - so the thing would need to know the languages it supports and it would need to be told how certain things are implemented (like there are no templates in Java). Imagine that I could say in that scripting language: Multiplications of two Complex numbers of doubles with values (1E-20, 0) (1E-20, 0) should result in a ComplexUnderflow exception. These were just some wild ideas coming to my mind as I am reading the intro to the use of CppUnit(*). Please do not take it as a criticism, but rather as sharing thoughts. (*) So it might be I am banging on an open door, since I have no idea if you have done this or plan to do it. Attila |