COIN-OR::LEMON - Graph Library

Opened 11 years ago

Closed 11 years ago

#30 closed defect (fixed)

Erroneous initialization of static members

Reported by: Akos Ladanyi Owned by: Peter Kovacs
Priority: major Milestone:
Component: core Version: svn trunk
Keywords: Cc:
Revision id:

Description

Only static integral constant members can be initialized by adding a constant-expression initializer to their member declaration. In practice this means:

class Foo {
  public:
    static const int a = 5;       // this is ok
    static const double b = 1.5;  // this is not ok
                                  // (double is not an integral type)
};

The correct form:

class Foo {
  public:
    static const int a = 5;
    static const double b;
};

const double Foo::b = 1.5;    // this line goes to the .cc file

Note that if (and only if) you need to use an initialized member in a way that requires it to be stored as an object in memory, the member must be defined somewhere. This means that for example if you need to take the address of Foo::a then you need to define it like Foo:b but the initializer may not be repeated:

const int Foo::a;    // in the .cc file

In case Foo is a class template the syntax is a bit trickier:

template<typename T>
class Foo
{
  public: 
    static const int a = 5;
    static const double b;
};

template<typename T>
const double Foo<T>::b = 1.5;    // in the .h file

The above described problem occurs at the following places in the SVN tree:

  • lemon/cycle_canceling.h:128
  • lemon/network_simplex.h:284
  • lemon/network_simplex.h:345
  • lemon/network_simplex.h:346

You can find these by invoking g++ with the -ansi and -pedantic flags (and by running make check).

Change History (3)

comment:1 in reply to:  description Changed 11 years ago by Alpar Juttner

Replying to ladanyi:

    static const int a = 5;       // this is ok
    static const double b = 1.5;  // this is not ok

This is amongst the things why I constantly beg for a well designed language that would replace C++.

By the way, doesn't it cause performance problem? If a constant is in the header file, then the optimizer will know its actual value, so it can optimize the expressions that use it. If the value of a constant appears only in a .cc file, it cannot.

Should we insist on using -ansi -pedantic?

comment:2 Changed 11 years ago by Peter Kovacs

Status: newassigned

Thank you, Akos. Actually I knew that whole thing, but I wasn't careful enough when I replaced #define commands with static const varibles.

I don't want .cc files for these header files, so I do prefer a solution that needs only header files.

What solution could you suggest? For the main class of a header file the necessary constants can be defined in the file itself outside the class. It is not so pretty, but maybe it is acceptable. However what can we do with member classes? Or should I use const int varibles, e.g. instead of 0.0015 use 15/10000?

comment:3 in reply to:  2 Changed 11 years ago by Peter Kovacs

Resolution: fixed
Status: assignedclosed

Replying to kpeter:

Or should I use const int varibles, e.g. instead of 0.0015 use 15/10000?

I used this solution in all the cases.

Note: See TracTickets for help on using tickets.