Skip to content

Code Style

Tim Hultman edited this page May 3, 2019 · 9 revisions

C++ Code Style

This is a page detailing C++ code style that shall be used in this project.

Functions

This section details the expected style for functions.

mixedCase vs underscore_lower_case function names

mixedCase shall be uniquely used for interface functions between QML and C++, underscore_lower_case shall be uniquely used between C++ objects or internal to a class. The rationale is that QML requires mixedCase for interfacing with C++, but the project did not start out as a QML project and underscore_lower_case was instead used. When switching to QML it was difficult to discern the QML interface from the "C++ internal" interface, so the distinction is kept by using mixedCase for QML interface and underscore_lower_case for everything else.

In other words: mixedCase: QML <--> C++, underscore_lower_case: C++ <--> C++.

Note that only a few files have to contain both QML interface and C++ interface as the design aims to decouple the GUI from the simulator as much as possible.

Function arguments

Function arguments shall use empty parenthesis if the function has no arguments, e.g. void foo(void) is "bad", void foo() is "good".

Pointer and reference notations (*/&) shall be placed next to the type, not the variable name. E.g. void foo(int* pointer) is "good", void foo(int *pointer) is "bad".

Class methods

No distinction is made (style-wise) between free functions and class methods.

Variables

This section contains the expected style for variables.

General variable names

Variable names shall be lower-case and use underscore as separator. Prefer clarity over initialisms/dropping vowels, e.g. hdr_f is "bad", header_file is "good".

Pointer/reference notation

Pointer and reference notations (*/&) shall be placed next to the type, not the variable name. E.g. void foo(int* pointer) is "good", void foo(int *pointer) is "bad".

Class members

The rules in General variable names apply to class member names.

this shall be used over prefixes/suffixes like m_<variable>, _<variable, <variable>_ or other such variations. Duplicate names for arguments and members is OK; use this to disambiguate the two when necessary. The exception to this rule is if this is not sufficient to resolve the difference (constructor initialization using arguments of types that would require a deep copy). In that case let the argument be named <variable>_.

Example "MyClass.h":

...
class MyClass {
public:   
    void set_foo(unsigned foo);

private:
    unsigned foo;
};

Example usage of this in "MyClass.cpp":

void MyClass::set_foo(unsigned foo) {
    this->foo = foo;
}

Header inclusion order and forward declarations

  1. Own class header for .cpp files, base class for .h files if applicable
  2. stdlibs + third party libs (e.g. Qt)
  3. CSIM headers
  4. Forward declarations (in header files)

Internal order shall be alphabetically sorted. If using QtCreator the hotkey is Alt + Shift + S (lines to sort must be selected first). Note that each section shall have 1 newline at the end of it, regardless if there is an upcoming section.

Example "MyClass.h":

... (include guard)
#include "Base.h"

#include <QVector>

#include "BarEnum.h"

class Foo;

class MyClass(Base) {
public:
    void set_bar(BarEnum);

private:
    QVector<int> vec;
    Foo* foo;
    BarEnum bar;
};

Example "MyClass.cpp" (unrelated to the previous example):

#include "MyClass.h"

#include <QSet>
#include <QVector>

#include "bar.h"
#include "baz.h"
#include "foo.h"

MyClass::MyClass():
...