Monday, 10 December 2012

Initialization Lists in C++

We all know, what happens when a class object is created; its Constructor is called. And, ofcorse that's not the end, it's base class constructor is also called. By default, the constructors invoked are the default ("no-argument") constructors. Moreover, all of these constructors are called before the class's own constructor is called.

So, with below piece of code,
class A 

          std::cout << "A's constructor" << std::endl; 

class B: public A
          std::cout << "B's constructor" << std::endl; 

int main() 
     B obj1;
     return 0;
The object "obj1" is constructed in two stages: first, the A's constructor is invoked and then the B's constructor is invoked. The output of the above program will be to indicate that A's constructor is called first, followed by B's constructor. We all know this.

Why do this? There are a few reasons. First, each class should need to initialize things that belong to it, not things that belong to other classes. So a child class should hand off the work of constructing the portion of it that belongs to the parent class. Second, the child class may depend on these fields when initializing its own fields; therefore, the constructor needs to be called before the child class's constructor runs. In addition, all of the objects that belong to the class should be initialized so that the constructor can use them if it needs to.

Initialization List:
But what if you have a parent class that needs to take arguments to its constructor?
This is where initialization lists come into play. An initialization list immediately follows the constructor's signature, separated by a colon(:). Initialization List is another or a better approach for initializing the member variables (and base class objects) of a class upon construction of an instance of it's own.

Let's modify above code to demonstrate initialization list,

class A 

     A(int x)
          std::cout << "A's constructor is called with x = "<< x << std::endl;

class B: public A
     B() : A(100) //initialization list - construct A part of B
          std::cout << "B's constructor" << std::endl; 

This is how you can construct and initialize base part of the child construct.

You can set-up order of constructors need to be called, before child constructor, separated by comma.
Like this,
class B: public A, public C
     B() : A(100), C(200)
          std::cout << "B's constructor" << std::endl; 

The above call will be in sequential, as before B constructor, A part of B is initialized and then C part of B is initialized and after that only B's constructor is executed.

Here are interesting factors about initialization list:

> Initialization List is used to initialize both user defined data types (like embedded object of a class) and also primitive/built-in data types (like int, char).
Yes basically it is possible, look at below example,

class A 

     A(int x)
          std::cout << "A's constructor is called with x = "<< x << std::endl;

class B: public A
     int x;
     int y;
     B() : A(100), x(25), y(50)
          std::cout << "B's constructor" << std::endl; 

Above code initializes A part of B, then initializes two member variables 'x' and 'y' with constant values, before calling B's own constructor.

> Initialization List can appear irrespective of the place the constructor is defined.

> Initializing the member variables in the Initialization List is better than initializing them inside the body of the constructor of the class.

> Data members are initialized in the order they are declared, regardless of the order of their initialization.

> It is mandatory to initialize Reference Data Member in an Initialization List because it can not exist without being initialized.

> It is mandatory to initialize Constant Data Member in an Initialization List otherwise it would be constrructed with some junk values and we cannot initialize it later anywhere else.

> It is mandatory to construct and initialize, embedded class objects/base class objects in case of inheritance, in an Initialization List, if they do not themselves have a zero-argument/default constructor provided.

Great isn't it !!!!

Tuesday, 4 December 2012

Virtual Inheritance and Diamond Problem in C++

Multiple inheritance in C++ is a powerful, but tricky tool, that often leads to problems if not used carefully. One of the major problem that arises due to multiple inheritance is the diamond problem.

The "diamond problem" (sometimes referred to as the "deadly diamond of death") is an ambiguity that arises when two classes B and C inherit from A, and class D inherits from both B and C. If D calls a method defined in A (and does not override the method), and B and C have overridden that method differently, then from which class does it inherit: B, or C?

                         Class A
                      /                 \  
               Class B         Class C 
                      \________ /    
                         Class D

Classic Example:

class Animal {
  virtual void eat();
class Mammal : public Animal {
  virtual void breathe();
class WingedAnimal : public Animal {
  virtual void flap();
// A bat is a winged mammal
class Bat : public Mammal, public WingedAnimal {
Bat bat;

As declared above, a call to is ambiguous because there are two Animal (indirect) base classes in Bat, so any Bat object has two different Animal base class sub-objects. So an attempt to directly bind a reference to the Animal sub-object of a Bat object would fail, since the binding is inherently ambiguous:

Bat b;
Animal &a = b; // error: which Animal subobject should a Bat cast into, 
               // a Mammal::Animal or a WingedAnimal::Animal?

Solution is in Virtual Inheritance:

And our re-implemented class looks like this,

class Animal {
  virtual void eat();
// Two classes virtually inheriting Animal:
class Mammal : public virtual Animal {
  virtual void breathe();
class WingedAnimal : public virtual Animal {
  virtual void flap();
// A bat is still a winged mammal
class Bat : public Mammal, public WingedAnimal {

The Animal portion of Bat::WingedAnimal is now the same Animal instance as the one used by Bat::Mammal, which is to say that a Bat has only one, shared, Animal instance in its representation and so a call to Bat::eat() is unambiguous. Additionally, a direct cast from Bat to Animal is also unambiguous, now that there exists only one Animal instance which Bat could be converted to.

This is implemented by providing Mammal and WingedAnimal with a vtable pointer (or "vpointer") since the memory offset between the beginning of a Mammal and of its Animal part is unknown until runtime. Thus Bat becomes (vpointer, Mammal, vpointer, WingedAnimal, Bat, Animal). There are two vtable pointers, one per inheritance hierarchy that virtually inherits Animal. In this example, one for Mammal and one for WingedAnimal. The object size has therefore increased by two pointers, but now there is only one Animal and no ambiguity. All objects of type Bat will have the same vpointers, but each Bat object will contain its own unique Animal object. If another class inherits from Mammal, such as Squirrel, then the vpointer in the Mammal object in a Squirrelwill be different from the vpointer in the Mammal object in a Bat, although they can still be essentially the same in the special case that the Squirrel part of the object has the same size as the Batpart, because then the distance from the Mammal to the Animal part is the same. The vtables are not really the same, but all essential information in them (the distance) is.

Reference variable in c++

C++ references allow you to create a second name for the a variable that you can use to read or modify the original data stored in that variable. While this may not sound appealing at first, what this means is that when you declare a reference and assign it a variable, it will allow you to treat the reference exactly as though it were the original variable for the purpose of accessing and modifying the value of the original variable--even if the second name (the reference) is located within a different scope. This means, for instance, that if you make your function arguments references, and you will effectively have a way to change the original data passed into the function. This is quite different from how C++ normally works, where you have arguments to a function copied into new variables. It also allows you to dramatically reduce the amount of copying that takes place behind the scenes, both with functions and in other areas of C++, like catch clauses.

Declaration is,
int& ref = <some_int_variable>;

For Example,
int x; 
int& foo = x; // foo is now a reference to x so this sets x to 56 
foo = 56; 
std::cout << x <<std::endl;

What are the difference between Reference Variable and conventional pointers?

> A pointer can be re-assigned any number of times while a reference can not be reassigned after initialization.
> A pointer can point to NULL while reference can never point to NULL
> You can't take the address of a reference like you can with pointers
> There's no "reference arithmetic" (but you can take the address of an object pointed by a reference and do pointer arithmetic on it as in &obj + 5).

End Line: Beware of references to dynamically allocated memory. One problem is that when you use references, it's not clear that the memory backing the reference needs to be deallocated--it usually doesn't, after all. This can be fine when you're passing data into a function since the function would generally not be responsible for de-allocating the memory anyway. 

On the other hand, if you return a reference to dynamically allocated memory, then you're asking for trouble since it won't be clear that there is something that needs to be cleaned up by the function caller.

Monday, 3 December 2012

Compile Qt Applications with custom Makefile

Hi folks, this is a quick post to "Compile Qt application using your own Makefile".
[ I am sure there is no link which explains about this !!! ]

Stuffs I have used:
[*] Qt 4.8.1 compiled and installed in my machine [how to do that?], with Visual C++ 10 compiler.
[*] Windows-7 operating system, 64-Bit.
[*] Knowledge about writing Makefile [ref] [I am not discussing how to write Makefiles here with this post]

So, our first step is to have one Qt application. For testing purpose you can use mine  [download-in-zip].
In my test application I have used all the stuffs that a common Qt developer needs to, like UI components, CPP files, H files and QRC files.
I will be referring to same test application shared above.

Before I start discussion, let me put all the codes in here first,

/* ----------------------------------------- */
/* File Name: main.cpp        */
/* ----------------------------------------- */
  1. #include <QtGui/QApplication>
  2. #include "mainwindow.h"

  3. int main(int argc, char *argv[])
  4. {
  5.     QApplication a(argc, argv);
  6.     MainWindow w;
  8.     return a.exec();
  9. }

/* ----------------------------------------- */
/* File Name: mainwindow.cpp        */
/* ----------------------------------------- */
  1. #include "mainwindow.h"
  2. #include "ui_mainwindow.h"
  3. #include <QPixmap>

  4. MainWindow::MainWindow(QWidget *parent) :
  5.     QMainWindow(parent),
  6.     ui(new Ui::MainWindow)
  7. {
  8.     ui->setupUi(this);
  9. }

  10. MainWindow::~MainWindow()
  11. {
  12.     delete ui;
  13. }

  14. void MainWindow::on_pushButtonShow_clicked()
  15. {
  16.     QPixmap pixmap(":/Image/butterfly.jpg");
  17.     ui->imageLabel->setPixmap(pixmap);
  18. }

/* ----------------------------------------- */
/* File Name: mainwindow.h        */
/* ----------------------------------------- */
  1. #ifndef MAINWINDOW_H
  2. #define MAINWINDOW_H

  3. #include <QMainWindow>

  4. namespace Ui {
  5. class MainWindow;
  6. }

  7. class MainWindow : public QMainWindow
  8. {
  9.     Q_OBJECT
  11. public:
  12.     explicit MainWindow(QWidget *parent = 0);
  13.     ~MainWindow();
  15. private slots:
  16.     void on_pushButtonShow_clicked();

  17. private:
  18.     Ui::MainWindow *ui;
  19. };

  20. #endif // MAINWINDOW_H

And UI file, mainwindow.ui has one QLabel named as "imageLabel" and one QPushButton named, "pushButtonShow".

And QRC file, "TestRsrc.qrc" has butterfly.jpg under one prefix name "/Image".

Now, let's look into Custom Makefiles.

I have divided Makefiles into 2 different parts, with respect to their operation.
First Makefile, under source main directory, defines rules for building Object files.
Second Makefile, under build directory defines rules for linking object files with Qt shared libraries, in general resolves symbol definition in objects.
And, Config file under build directory, as name indicates, has some of the common configuration definitions for compilation.
Below are the Makefiles and Config files,

  1. ####### Config file

  2. CXX           = cl



  5. CXXFLAGS      = -nologo -Zc:wchar_t- -GR -EHsc -MDd -W3 -w34100 -w34189 /Od $(DEFINES) -c

  6. QT_PATH  = C:\QtSDK\Desktop\Qt\4.8.0\msvc2010

  7. INCPATH       = -I"$(QT_PATH)\include" -I"$(QT_PATH)\include\QtCore" -I"$(QT_PATH)\include\QtGui" -I"." -I"..\..\Sources" -I"." -I"$(QT_PATH)\mkspecs\win32-msvc2010" 

  8. LNK           = link.exe


  10. QT_LIBS       = $(QT_PATH)\lib\qtmaind.lib $(QT_PATH)\lib\QtGuid4.lib $(QT_PATH)\lib\QtCored4.lib 

  11. ADD_LIB  = 

  12. MFLAGS  = -D_MSC_VER=1500 -DWIN32

  13. QMOC  = $(QT_PATH)\bin\moc.exe

  14. QRCC  = $(QT_PATH)\bin\rcc.exe

  15. ####### Output format

  16. PATH_SEP  = ^\
  17. SRCDIR  = ..$(PATH_SEP)
  18. OBJDIR    = .$(PATH_SEP)
  19. OBJECT_SUFIX  = obj
  20. DESTDIR       = .$(PATH_SEP)
  21. TARGET        = TestApp
  22. TARGET_SUFIX  = exe
  23. OUTPUT  = TestApp.$(TARGET_SUFIX)

Makefile, which resides under Build directory,

  1. ####### Makefile for Linking apps #######
  2. ####### Reside under Build directory #######
  3. ####### Basically resolves symbol definitions for objects #######

  4. ####### Includes

  5. include Config
  6. include ..\Makefile

  7. ####### Main Build rules

  8. all: $(OBJECTS) $(TARGET)

  9. $(TARGET): $(OBJECTS) 
  10. $(LNK) $(OBJECTS) $(ADD_LIB) $(QT_LIBS) $(LFLAGS) /out:$(OUTPUT)
  11. clean:
  12. del *.$(OBJECT_SUFIX) *.$(TARGET_SUFIX) moc_*.cpp qrc_*.cpp *.pdb *.manifest 

Makefile, which resides under main source directory,

  1. ####### Makefile for building objects #######
  2. ####### Reside under main source directory #######
  3. ####### Rules and definitions for building objects and other dependencies #######

  4. default:all

  5. ####### Source Files

  6. SOURCES       = $(SRCDIR)main.cpp \
  7. $(SRCDIR)mainwindow.cpp

  8. MOC_SRC  = moc_mainwindow.cpp 
  9. QRC_SRC  = qrc_TestRsrc.cpp
  10. ####### Object Files
  11. CORE_OBJ      = main.$(OBJECT_SUFIX) \
  12. mainwindow.$(OBJECT_SUFIX)

  13. MOC_OBJ  = moc_mainwindow.$(OBJECT_SUFIX)
  14. QRC_OBJ  = qrc_TestRsrc.$(OBJECT_SUFIX)


  16. ####### MOC Source Build rules

  17. moc_mainwindow.cpp: $(SRCDIR)mainwindow.h
  18. $(QMOC) $(DEFINES) $(INCPATH) $(MFLAGS) $(SRCDIR)mainwindow.h -o moc_mainwindow.cpp

  19. ####### QRC Source Build rules

  20. qrc_TestRsrc.cpp: $(SRCDIR)TestRsrc.qrc
  21. $(QRCC) -name TestRsrc $(SRCDIR)TestRsrc.qrc -o qrc_TestRsrc.cpp

  22. ####### Core Object Build rules

  23. main.$(OBJECT_SUFIX): $(SRCDIR)main.cpp
  24. $(CXX) $(SRCDIR)main.cpp $(INCPATH) $(CXXFLAGS) main.$(OBJECT_SUFIX)

  25. mainwindow.$(OBJECT_SUFIX): $(SRCDIR)mainwindow.cpp
  26. $(CXX) $(SRCDIR)mainwindow.cpp $(INCPATH) $(CXXFLAGS) mainwindow.$(OBJECT_SUFIX)
  27. ####### MOC Object Build rules

  28. moc_mainwindow.$(OBJECT_SUFIX): moc_mainwindow.cpp
  29. $(CXX) moc_mainwindow.cpp $(INCPATH) $(CXXFLAGS) moc_mainwindow.$(OBJECT_SUFIX)
  30. ####### QRC Object Build rules

  31. qrc_TestRsrc.$(OBJECT_SUFIX): qrc_TestRsrc.cpp
  32. $(CXX) qrc_TestRsrc.cpp $(INCPATH) $(CXXFLAGS) qrc_TestRsrc.$(OBJECT_SUFIX)

If you have used command line compilation for VC++, by this time you must have understood above Config and Makefiles. I cannot explain command line compilation and other basic stuffs here, but will try to clarify as much as possible.

If you look into Config file,
Line number 3: says compiler we going to use is CL (VC++ command line compiler).
Line number 5: gives some of the Qt standard definitions needed for compilation. -D<definition> or /D<definition> is a flag to define them in CL.
Line number 7: is custom definitions or user definitions. If you have any specific pre-compilation definitions, then you can define them here with flag -D or /D.
Line number 9: is standard CPP and Qt flags used to compile CPP application in CL.
Line number 11: says compiler where to refer for Qt related stuffs compilation. This is where my Qt was installed, you have to change this path to your Qt installation path before you compile.
Line Number 13: is reference path for include files you have used in your application. If you have included any specific files in your program other than mentioned here, you have to include them here.
Line number 15 and 17: says our linking application is link.exe and some standard flags for linking.
Line number 19: says Qt shared libraries (lib files) required to resolve symbols and definitions used in application. If you have referenced any other Qt libraries, for example QtNetwork, you have to include that library here.
Line number 21: is for further development, which gives you option to include and link additional libraries or 3rd party libraries you have referenced in your application.
Line number 23: is flag for generating MOC objects.
Line number 25 and 27: this defines path for moc and rcc apps, which is required to build moc objects and objects out from q-resource files. This apps are part of your Qt installation.
Line 31 to 38 define some of the relative path for where to find elements and output format.

The Makefile under build directory, is quite simple.
It includes definitions and rules from Config and other Makefile. It has 3 rules viz., which builds Objects first and then Target exe will be linked with libs and objects. These are the general Makefile rules I have used and nothing much to say about them.

Now, let me brief some about Makefile under main source directory.
This Makefile contains basic rules to build objects out from standard CPP files, MOC files and QRC files.
Remember steps to build the objects,
> MOC objects and QRC objects should be built before you build CPP objects.
> Header files (.h files), having Q_OBJECT macro definition in their class, needs only be generated MOC files. Other header files can be treated as normal CPP headers.
> Before you build MOC and QRC objects, you have to use moc.exe and rcc.exe apps to build their corresponding CPP files.
So look into Makefile, Line number 9, 12 and 14 says we have 4 CPP source files need to be compiled into Objects.
Line number 25 says we have 3 types of objects, need to be built in order specified.
If you look into Moc source build rules, that is line number 29 and 30, it uses moc.exe app to generate moc_mainwindow.cpp source file corresponding header "mainwindow.h". To know more about building Moc objects in Qt, refer here.
Line number 34 and 35 says standard rules to build QRC source file.
Refer naming conventions for building Moc and QRC files; they have moc_<filename>.cpp and qrc_<filename>.cpp; and their corresponding object files will be moc_<filename>.obj and qrc_<filename>.obj after built. This is how it has to be, and follow the same convention for better understanding.
At this point we have all 4 source files ready to build into objects. Use CPP standard method to build all source files into objects. Don't forget to specify proper paths for your build.

That is all about your custom Makefiles, used to build your Qt application.

If you have downloaded my sample application, which I have shared above, try to build it with Visual C++ command line.
Unzip the file into safe location (say c:\testapp)
Open Config file, inside build directory, with any text editor and change "Qt_PATH" definition to corresponding Qt installation path in your machine.
Go to Start > All Programs > Microsoft Visual Studio 2010 > Visual Studio Tools, and open "Visual Studio Command Prompt 2010".
Navigate to the location c:\testapp and then navigate inside "build" directory.
Give command "nmake all"
This should build your exe. In order to run the exe, you have to keep corresponding runtime DLLs inside the directory where exe is executing from. So copy two files QtCored4.dll and QtGuid4.dll from your Qt installation path into build directory and run the application.
To clen the build, execute command "nmake clean".

Hope this is helpful.