Can I initialize a static const member at run-time in C++? - c++

Is it possible to initialize a static const member of my class during run-time? This variable is a constant throughout my program but I want to send it as a command-line argument.
//A.h
class A {
public:
static const int T;
};
//in main method
int main(int argc,char** argv)
{
//how can I do something like
A::T = atoi(argv[1]);
}
If this cannot be done, what is the type of variable I should use? I need to initialize it at run-time as well as preserve the constant property.

You cannot rely on data produced after your main has started for initialization of static variables, because static initialization in the translation unit of main happens before main gets control, and static initialization in other translation units may happen before or after static initialization of main translation unit in unspecified order.
However, you can initialize a hidden non-const variable, and provide a const reference to it, like this:
struct A {
public:
// Expose T as a const reference to int
static const int& T;
};
//in main.cpp
// Make a hidden variable for the actual value
static int actualT;
// Initialize A::T to reference the hidden variable
const int& A::T(actualT);
int main(int argc,char** argv) {
// Set the hidden variable
actualT = atoi(argv[1]);
// Now the publicly visible variable A::T has the correct value
cout << A::T << endl;
}
Demo.

I am sorry to disagree with the comments and answers saying that it is not possible for a static const symbol to be initialized at program startup rather than at compile time.
Actually this IS possible, and I used it many times, BUT I initialize it from a configuration file. Something like:
// GetConfig is a function that fetches values from a configuration file
const int Param1 = GetConfig("Param1");
const int MyClass::Member1 = GetConfig("MyClass.Member1");
As you see, these static consts are not necessarily known at compile time. They can be set from the environment, such as a config file.
On the other hand, setting them from argv[], seems very difficult, if ever feasible, because when main() starts, static symbols are already initialized.

No, you cannot do that.
If this cannot be done what is the type of variable I should use ?
You can use a non-const member.
class A
{
public:
static int T;
};
int A::T;
Another option is to make T a private member, make main a friend so only it can modify the value, and then expose the member through a function.
#include <cstdlib>
class A
{
public:
static int getT() { return T; }
private:
static int T;
friend int main(int argc, char** argv);
};
int A::T;
int main(int argc, char** argv)
{
A::T = std::atoi(argv[1]);
return 0;
}

Not only you can't, you should not try doing this by messing with const_cast. Static const members have a very high chance of ending up in read-only segment, and any attempt to modify them will cause program to crash.

Typically you will have more than one configuration value. So put them in a struct, and the normal global access to it is const.
const config* Config;
...
main (int argc, char* argv [])
{
Config= new config (argc, argv);
...
}
You can get fancier and have a global function to return config, so normal code can't even change the pointer, but it is harder to do that by accident.
A header file exposes get_config () for all to use, but the way to set it is only known to the code that's meant to do so.

No, since you defined the variable as static and const, you cannot change its value.
You will have to set its value in the definition itself, or through a constructor called when you create an object of class A.

Method #1: Initialize a hidden non-const variable, and provide a const reference to it (as shown by dasblinkenlight):
class A {
public:
static const int &T;
};
static int dummy = 0;
const int &A::T = dummy;
int main() {
dummy = 10;
std::cout << A::T << std::endl;
}
Live Demo
Method #2: Use a non const static member (as shown by R Sahu):
class A {
public:
static int T;
};
int A::T = 0;
int main() {
A::T = 10;
}
Live Demo
Method #3: Declare a hidden non-const variable as a private static member of your class and provide a static member const reference to interface it. Define a friend function as inititalizer:
class A {
friend void foo(int);
static int dummy;
public:
static const int &T;
};
const int &A::T = A::dummy;
int A::dummy = 0;
void foo(int val) { A::dummy = val; }
int main() {
foo(10);
std::cout << A::T << std::endl;
}
Live Demo
Method #4: Declare a hidden non-const variable as a private static member of your class and provide a static member const reference to interface it. Define a static member function as inititalizer:
class A {
static int dummy;
public:
static const int &T;
static void foo(int val) { A::dummy = val; }
};
const int &A::T = A::dummy;
int A::dummy = 0;
int main() {
A::foo(10);
std::cout << A::T << std::endl;
}
Live Demo
Bonus:
If you want to initialize only once you can change the helper function to:
static void foo(int val) {
static bool init = true;
if(init) A::dummy = val;
init = false;
}
Live Demo

Having been facing the same problem myself lately I found #A.S.H 's answer to be the closest to perfect but the fact that the variables have to be initialized so early can cause some problems:
Can't use data sources that aren't available yet, such as argc and argv as per the question.
Some dependencies might not be initialized yet. For example, many a GUI framework does not allow creating textboxes that early on yet. This is a problem because we might want to display a error textbox if loading the configuration file fails to inform the user.
So I came up with the following:
template <class T>
class StaticConfig
{
public:
StaticConfig()
{
if (!mIsInitialised)
{
throw std::runtime_error("Tried to construct uninitialised StaticConfig!");
}
}
const T*
operator -> () const
{
return &mConfig;
}
private:
friend class ConfigHandler;
StaticConfig(const T& config)
{
mConfig = config;
mIsInitialised = true;
}
static T mConfig;
static bool mIsInitialised;
};
template <class T>
T StaticConfig<T>::mConfig;
template <class T>
bool StaticConfig<T>::mIsInitialised = false;
We make our data static but non-const so we don't have to initialize it immediately and can assign the correct values to it at a more opportune time. Read only access is given trough a overload of operator -> The default constructor checks if a StaticConfig of this type has already been loaded with valid data and throws if it is not. This should never happen in practice but serves as a debugging aid. A private constructor allows loading the type with valid data. A ConfigHandler class, responsible for loading the data, is made a friend so it can access the private constructor.
A ConfigHandler instance can be briefly created at an opportune time when all the dependencies are available to initialize all the StaticConfig types. Once done, the ConfigHandler instance can be discarded. After that, a class can simply include the appropriate type of StaticConfig as a member and read-only access the data with minimal intrusion.
Online demonstration.

N - O
The semantics of what is being required are all wrong, and you shouldn't use a static-const for that.
A static is an object or integral type which has static storage duration and internal linkage.
A const is an object that does not change its value throughout application's lifetime, any attempt to change it results in UD . ( the overwhelming majority of such cases is a pretty well defined crash )
As a result of this question dangerous workarounds have been proposed to mimic the implied behavior. In most of examples a static-const-reference is given a somehow hidden static which is assignable at runtime, e.g. this.
Apart from the difficulties in maintaining such code, the problem remains that declared semantics are not actually enforced.
For example in keeping the value const throughout the application runtime can be hacked by doing const_cast<int &>(A::T) = 42 , which is perfectly valid, perfectly define code since the referenced type is not const.
What is being sought after here is an class that permits to be initialized only once throughout the application, has internal linkage, and the lifetime of the application.
So just do a template class that does that:
template<typename V> class fixation
{
bool init = true;
V val;
public:
fixation(V const & v) : init(true), val(v) {}
fixation & operator=( fixation arg)
{
if(init )
{
this->val = arg.val;
}
this->init = false;
return *this;
}
V get()
{
return val;
}
};
struct A
{
static fixation<int> T;
};
How to handle the case that it is called a second time, that is an implementation decision. In this example the value is totally ignored. Others may prefer to throw an exception, do an assertion, ... etc.

There is a trick, but you should probably avoid it! Here's a bare bones example to illustrate the principle:
int const& foo(int i) {
static const int j = (i == 0 ? throw 0 : i);
return j;
}
int main() {
try {
int x = foo(0); // oops, we throw
} catch(...) {}
int x = foo(1); // initialized..
int y = foo(0); // still works..
}
Careful!

Use a Singleton Pattern here.
have a data member which you'd like to initialize at run time in the singleton class. One a single instance is created and the data member is properly initialized, there would be no further risk of overwriting it and altering it.
Singleton would preserve the singularity of your data.
Hope this helps.

Related

Accessing easily from static function to non static members

I have class A with a static function S and it has as a parameter the pointer to an instance of A.
class A {
int v;
int f(int v2) { return v2*2;}
public:
static int S(A *ptA);
}
I want to access to the non static members of A so in the definition I can do..
int S(A *ptA) {
return ptA->f(ptA->v);
}
But unfortunately S is to much complex and v is not only one variable...
So the question is: Is there a way to set inside a static function the value of this pointer... something like this=ptA or using ptA as this or whatever to avoid having to use ptA-> all the time.

When to use member variable pointer

Following is some example code for using "member variable pointer".
#include <iostream>
using namespace std;
struct CData {
int m_x;
int m_y;
};
int main() {
CData obj = {10, 20};
int CData::*pData = &CData::m_x;
cout << obj.*pData << endl;
return 0;
}
http://ideone.com/hJyWP9
From this example, I am not quire sure when I should use the member variable pointer.
Could you inform me some benefits or example of using the member variable pointer?
I think this is much more useful for functions rather than variable members, but the same principal applies to both.
Say I have a class with 3 functions that do one thing which depends on something such as the processor you are running with (i.e. INTEL versus AMD, or processor that supports SSE4 versus an older process with only SSE2...)
void renderCPU();
void renderSSE2();
void renderSSE3();
void renderSSE4();
Then you'd take the pointer of one of these functions and use the pointer instead of testing whether you have SSE4, SSE3, SSE2, or CPU each time you want to render.
// in constructor
if (SSE4) render_ptr = &C::renderSSE4;
else if (SSE3) render_ptr = &C::renderSSE3;
else if (SSE2) render_ptr = &C::renderSSE2;
else render_ptr = &C::renderCPU;
// And in the render function:
this->*render_ptr();
For variable members, similar things could happen, although frankly I never used that for a variable, probably because you can also use a straight pointer (i.e. an 'int *' in your example...) Although I guess it would be a good idea to use class pointers for added security.
Now, I recall, a while back, using a class with a public const reference pointer to a variable member that was private. In effect, it was giving the user a getter() without having to actually call a function. One problem with that technique is that the reference is locked on construction.
class P
{
private:
int v_;
public:
const int& value;
p()
: value(v_) // locked...
{
}
};
A class variable pointer would allow you to change the pointer while using the object.
class P
{
private:
int x_;
int y_;
int z_;
public:
const int P::*ref;
p()
: ref(&P::x_) // not locked...
{
}
void modeX()
{
ref = &P::x_;
}
void modeY()
{
ref = &P::y_;
}
void modeZ()
{
ref = &P::z_;
}
};
With such a class you should be able to do something like:
P p;
cout << p.*p.ref; // write x_
p.modeZ();
cout << p.*p.ref; // write z_
This makes 'value' quite safe, opposed to a bare pointer.
Note also that gives you the ability to write the following:
P p, q;
p.*q.ref = q.*p.ref;
Which may be useful to some people...

Can I call directly operator() without creating a temporary object?

I've the following utility function to convert a given string to integer.
class convertToInt:public std::unary_function<const char*, int>
{
public:
int operator()(const char* cNumber)
{
try
{
int result = boost::lexical_cast<int>(cNumber);
return result;
} catch ( boost::bad_lexical_cast& error)
{
std::cerr << "Error in converting to number "<< error.what() << std::endl;
return -1;
}
}
};
When I want to actually use this utility function, I've to do the following.
convertToInt cStrToInt;
int iNumberToCheck = cStrToInt(argv[1]);
I'm just wondering, is there a way, I can directly call
int iNumberToCheck = convertToInt(argv[1]);
No, it is a member function and requires an object for it to be invoked on. You could use an unnamed temporary instead:
int iNumberToCheck = convertToInt()(argv[1]);
You can make the function static, so that it does not require an instance. The call has to be scoped.
You can also create the temporary as part of your larger expression (rather than using a named variable), which may seem less efficient but in practice is probably optimized to the same thing by your compiler.
Edit to add: static won't work for operator(), so you would need to rework to use that option.
If you know the name of the functor at the call-site, then you why not just turn it into a function?
int convertToInt(const char* cNumber)
{
/*...*/
}
int iNumberToCheck = convertToInt(argv[1]);
Just create a statically-initialized global variable, which helps avoid the static initialization order fiasco. Static initialization requires the class to be an aggregate type. Just use the braces to initialize it:
struct convertToIntF
{
int operator()(const char* cNumber) const
{
try
{
int result = boost::lexical_cast<int>(cNumber);
return result;
}
catch ( boost::bad_lexical_cast& error)
{
std::cerr << "Error in converting to number "<< error.what() << std::endl;
return -1;
}
}
};
convetToIntF converToInt = {};
Now, if the function object stores state or inherits from a class that is not an aggregate, this won't work. However, in C++11, its fairly trivial to write an adaptor that can static initialize any default constructible function object:
template<class F>
struct static_
{
template<class... T>
auto operator()(T && ... x) const -> decltype(F()(std::forward<T>(x)...))
{
static F f;
return f(std::forward<T>(x)...);
}
};
Then it can be initialized like this:
static_<convetToIntF> converToInt = {};
In this very simple case, an anonymous object will probably work fine, as others have pointed out. If you have a more complex class with state, however, consider the singleton pattern:
class SingletonFunctor
{
private:
// some private state
// for a hybrid approach, the constructor could be public
SingletonFunctor()
{
// initialize state
}
public:
static const SingletonFunctor& GetSingleton()
{
static const SingletonFunctor _singleton;
return _singleton;
}
SomeType operator() (SomeOtherType param) const
{
// do something interesting
}
};
int main (void)
{
SomeType firstVal = SingletonFunctor::GetSingleton()(SomeOtherType());
// ...
// later
// no need to instantiate another object
SomeType secondVal = SingletonFunctor::GetSingleton()(SomeOtherType());
}
Be careful with this pattern if you mutate state, it can then have all the same problems as a global variable (especially with multithreading).

how to design overloaded member functions with const and volatile while designing API?

Let's assume you are writing a small library or an API that will be distributed to other programes,
that means you never know how other programers will create objects: will such an object be const, volatile, const volatile or it will be just an plain object.
normaly when we declare some class we do it so:
class A // THIS CLASS DOES NOT SUPPORT ANYTHING
{
public:
int get() { return x; }
private:
int x;
};
however if you want your class to support const objects you'll overload member function with const qualificator:
class B // THIS CLASS SUPPORTS CONST OBJECTS
{
public:
int get() { return x; }
int get() const { return x; }
private:
mutable int x;
};
more futer maybe we want also to support volatile but not const for our class:
class C // THIS CLASS SUPPORTS VOLATILE OBJECTS
{
public:
int get() { return x; }
int get() volatile { return x; }
private:
int x;
};
BUT what if user will use a object that is const or volatile or
what if user will use a object that is volatile and const in same time?
then we should add support for that too!
class D // THIS CLASS SUPPORTS CONST, VOLATILE AND CONST VOLATILE OBJECTS
{
public:
int get() { return x; }
int get() const { return x; }
int get() volatile { return x; }
int get() const volatile { return x; }
private:
mutable int x;
};
now let's see why would we want our class to have those 4 overloads:
// EXAMPLE
int main()
{
// figure 1
const A a ;
a.get(); // ERROR
// figure 2
volatile B b;
b.get(); // ERROR
// figure 3
const volatile C c;
c.get(); // ERROR
// figure 4 where we finaly created a super class capable of anything!!
const volatile D d;
d.get(); // NOW IS OK!
cin.ignore();
return 0;
}
well in this last example (figure 4) we can be shore that our class is capable to be instatated of any type
that means other programers will not have problem to create volatile, const or volatile const object of your class!
my question is:
is it a good design practice to overlaod each method four times?
if not why not?
also if our class has let's say 20 methods then it will acctualy have 80 methods when you overload them all!
EDIT:
does real world API classes do such thing?
if not, then how would we create volatile or const volatile object of that class if let's say we have such need.
My opinion is that in the real world:
Volatile is not widely used, and when it is it modifies always basic types. But never objects, so you never need to override a volatile member function.
const should be added to the member functions, not thinking in whether it will be needed by a const client code, but think instead if the operation the member function does is conceptually constant. That is called const correctness:
a. First of all, the function should do just one thing. Maybe one complex thing, but describable as a single concept.
b. Then, ask yourself whether this thing the function does changes the observable state of the object. If it does, then the function should not be constant. And if it does not, then declare it as constant.
When a client code wants to use your class, it will have a const reference when it is not allowed to modify the state of the object, and all will just work.
Note that I talked about the observable state of the object, not the actual contents of the member variables: that is an implementation detail.

Why we need to put const at end of function header but static at first?

I have code like this...
class Time
{
public:
Time(int, int, int);
void set_hours(int);
void set_minutes(int);
void set_seconds(int);
int get_hours() const;
int get_minutes() const;
int get_seconds() const;
static void fun() ;
void printu() const;
void prints();
private:
int x;
int hours;
int minutes;
int seconds;
const int i;
};
Why do I need to put const at last to make a function constant type but if i need to make a function, I can do this like...
static void Time::fun()
{
cout<<"hello";
}
Above function fun() is also in same class. I just want to know what is the reason behind this?
with a const instance method such as int get_hours() const;, the const means that the definition of int get_hours() const; will not modify this.
with a static method such as static void fun();, const does not apply because this is not available.
you can access a static method from the class or instance because of its visibility. more specifically, you cannot call instance methods or access instance variables (e.g. x, hours) from the static method because there is not an instance.
class t_classname {
public:
static void S() { this->x = 1; } // << error. this is not available in static method
void s() { this->x = 1; } // << ok
void t() const { this->x = 1; } // << error. cannot change state in const method
static void U() { t_classname a; a.x = 1; } // << ok to create an instance and use it in a static method
void v() const { S(); U(); } // << ok. static method is visible to this and does not mutate this.
private:
int a;
};
The const in the end means the function is constant, so it doesn't change the object's state.
When you put the const in the end, you can't change the state of the object's members.
Declaring a function static means it doesn't belong to the object at all, it belongs to the class type.
Putting const in the beginning means the return type value is a constant.
When you put const at the beginning, you're applying it to the return type. This doesn't matter if you're return type if void, but lets say you're returning char* that is not const. If you put const at the beginning, you'd end up with
static const char* MyFunction() { ... }
That tells me that the return type is a const char*, not a const function that returns a char*.
Putting it at the end avoids this problem.
It is because that if you put the const first it would mean that you are returning a const thing from the function - i.e. a different meaning that the function is const
It's a purely grammatical issue. const is a cv-qualifier and, when applied to a member function, must be placed after the parameter declarations. It you attempted to place it before the function name it could only be interpreted as qualifying the return type of the function.
static, on the other hand, is a storage class specifier and must appear before the declarator to which it applies.
These rules just flow from the way the C++ grammar is defined.
It is because that if you put the const first it would mean that you are returning a const thing from the function
One and another is explained a bit more in detail here. Putting const after a function declaration makes the function constant, meaning it cannot alter anything in the object that contains the function.