I'm pretty sure that the following question already has a good answer somewhere else, but it's difficult to find since I do not know the "name" of my problem.
I'm designing a class/object/"something" with the following properties:
So this sounds like a static template class:
template <int T>
class LookupTable{
public:
static void init(){
// create entries depending on T
}
private:
static vector<Entries> entries;
}
What I dislike is that I need to call init()
somewhere in my program. So the first question is: How can I make this class fully self-contained, with no need to be explicitly initialized somewhere?
Second part: What is the general design approach to implement such a class? I would be perfectly happy with a link to a good example.
A possible candidate is the singleton. But I have some doubts:
- The singleton considered bad design in many cases. Is it fine for a lookup table as described?
- Singleton is somewhat long notation, since I have to use LookupTable::getInstance()->getEntry(idx)
.
In C, static variables can only be initialized using constant literals.
To initialize the const value using constructor, we have to use the initialize list. This initializer list is used to initialize the data member of a class. The list of members, that will be initialized, will be present after the constructor after colon. members will be separated using comma.
The constructors should be used to initialize member variables of the class because member variables cannot be declared or defined in a single statement. Therefore, constructors are used in initializing data members of a class when an object is created.
A class declaration can contain static object of self type, it can also have pointer to self type, but it cannot have a non-static object of self type.
Singleton is the pattern, but use the safer variant where this approach avoids static initialization order fiasco and thread race conditions and since you complained about the length - we can shorten it a bit further passing the indices through the get_entry function:
template <int T>
class LookupTable{
public:
static std::vector<Entry> make_entries(){ ...}
static const std::vector<Entry>& get_entries(){
static const std::vector<Entry> instances = make_entries();
return instances;
}
static const Entry& get_entry(size_t idx){
return get_entries()[idx];
}
};
Another approach that avoids all the evils of a singleton are not to use a singleton - just pass a regular old class in directly as just another parameter. I do this with many crc function implementations with relatively heavy tables... most stuff won't care and then you don't have to wig out on design patterns. And it's faster.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With