blob: 7b08ea802bf19ac989afaef29bc55f89dda2e560 [file] [log] [blame]
/*
* Unit test of InstanceCounter class
*/
#include <iostream>
#include <string>
#include "boost/test/unit_test.hpp"
#include "printer/OutStream.h"
#include "base/InstanceCounter.h"
using namespace std;
using namespace sep;
// Local fixtures
OutStream os(&cout);
class A : public InstanceCounter<A> {}; // Regular case
class B : public A {}; // To see what happens with heritage
class C : public A, public InstanceCounter<C> {}; // To see what happens with multiple heritage
BOOST_AUTO_TEST_SUITE(Base);
BOOST_AUTO_TEST_CASE(t_InstanceCounter_all) {
// Due to the nature of the tested mechanism (instance counting), we are unable to create
// multiple independent unit test cases (as we should have been)
// Hence all assertions are checked within the same big test case
A::showCounters(os, "A");
// No instance created
BOOST_CHECK(A::INSTANCE_ALIVE == 0);
BOOST_CHECK(A::INSTANCE_CREATED == 0);
// Instance created as an automatic variable
A a1;
a1.showCounters(os, "A");
BOOST_CHECK(a1.INSTANCE_ALIVE == 1);
BOOST_CHECK(a1.INSTANCE_CREATED == 1);
// Instance created as an automatic variable in a subblock ...
{
A a2;
a2.showCounters(os, "A");
BOOST_CHECK(a2.INSTANCE_ALIVE == 2);
BOOST_CHECK(a2.INSTANCE_CREATED == 2);
}
// ... should be automatically deleted outside the block
a1.showCounters(os, "A");
BOOST_CHECK(a1.INSTANCE_ALIVE == 1);
BOOST_CHECK(a1.INSTANCE_CREATED == 2);
// Reference on existing instance
A& ra1 = a1;
a1.showCounters(os, "A");
BOOST_CHECK(ra1.INSTANCE_ALIVE == 1);
BOOST_CHECK(ra1.INSTANCE_CREATED == 2);
BOOST_CHECK(a1.INSTANCE_ALIVE == ra1.INSTANCE_ALIVE);
BOOST_CHECK(a1.INSTANCE_CREATED == ra1.INSTANCE_CREATED);
// Pointer on existing instance
A* pa1 = &a1;
a1.showCounters(os, "A");
BOOST_CHECK(pa1->INSTANCE_ALIVE == 1);
BOOST_CHECK(pa1->INSTANCE_CREATED == 2);
BOOST_CHECK(a1.INSTANCE_ALIVE == pa1->INSTANCE_ALIVE);
BOOST_CHECK(a1.INSTANCE_CREATED == pa1->INSTANCE_CREATED);
// Instance created on the heap ...
A* pa3 = new A();
pa3->showCounters(os, "A");
BOOST_CHECK(pa3->INSTANCE_ALIVE == 2);
BOOST_CHECK(pa3->INSTANCE_CREATED == 3);
// ... then deleted
delete pa3;
a1.showCounters(os, "A");
BOOST_CHECK(a1.INSTANCE_ALIVE == 1);
BOOST_CHECK(a1.INSTANCE_CREATED == 3);
// Counting mecanism should works through heritage relations
B b; // Remind : B is a A
b.showCounters(os, "B");
BOOST_CHECK(b.INSTANCE_ALIVE == 2);
BOOST_CHECK(b.INSTANCE_CREATED == 4);
// and through upcast
A a4 = (A) b; // Upcast changes nothing
a4.showCounters(os, "A");
BOOST_CHECK(a4.INSTANCE_ALIVE == 2);
BOOST_CHECK(a4.INSTANCE_CREATED == 4);
// What happens with multiple heritage
C c;
// c.showCounters(cout, "C"); // Doesn't compile due to the ambiguity of showCounters() in the multiple heritage (normal)
// In this case we have to choose which counter we want to query :
c.InstanceCounter<C>::showCounters(os, "C"); // C: 1/1
c.InstanceCounter<A>::showCounters(os, "A"); // A: 3/5
BOOST_CHECK(c.InstanceCounter<C>::INSTANCE_ALIVE == 1);
BOOST_CHECK(c.InstanceCounter<C>::INSTANCE_CREATED == 1);
BOOST_CHECK(c.InstanceCounter<A>::INSTANCE_ALIVE == 3);
BOOST_CHECK(c.InstanceCounter<A>::INSTANCE_CREATED == 5);
}
BOOST_AUTO_TEST_SUITE_END(); // BASE