0

Say I have base class Validator.

class Validator
{
public:
  void validate(const string& str)
  {
    if( k_valid_keys.find(str) == k_valid_keys.end() ) 
      throw exception();
  }
private:
  const static std::set<string> k_valid_keys;
};

Now assume I need to extend class Validator. Each derived class will have its own set of valid keys.
My goal is:

  1. keep k_valid_keys a member of Validator. No need to add it to each derived classes especially when there are more than a few types of those.
  2. keep k_valid_keys static. Assume I have multiple instances of Validator (and its derived classed) and initialization of k_valid_keys is expensive.

How can I initialize static member polymorphically? well, I know that it can't be done (please correct if I'm wrong).

So Assuming it can't be done, any idea of a better design for this problem?

idanshmu
  • 5,061
  • 6
  • 46
  • 92

3 Answers3

2

Since k_valid_keys is static declared at Validator, all the derived classes from Validator will share the same instance of k_valid_keys. That's it, you will not be able to have more than one instance of a subclass of Validator at the same time in your program, else your different instances of subclases of Validator will add elements to the same structure.

That's is, a static member variable on a class is just a global variable of your entire program.

If you have two or more subclases of Validator but you guarantee that you are going to have only just one instance, you just initialize k_valid_keys on the subclass constructor.

vz0
  • 32,345
  • 7
  • 44
  • 77
  • You are right. thanks for clarifying this. So I assume that what I'm asking for is not feasible? – idanshmu Mar 26 '14 at 10:03
  • @idanshmu IMHO Too many constraints, I guess. Why do you need k_valid_keys static? Performance? – vz0 Mar 26 '14 at 10:39
  • because it is static in nature. it shouldn't be bound to an instance since it is constant per `Validator` class. I failed to understand that my constrains makes not sense. – idanshmu Mar 26 '14 at 10:41
  • @idanshmu What about moving the static k_valid_keys field to each subclass? – vz0 Mar 26 '14 at 11:02
  • That's what I have to do. I was trying to avoid that because I didn't understand that I can't have multiple definitions for `static` member ( as you correctly stated ). I was trying to keep subclass as clean as possible but it can't be done that way. – idanshmu Mar 26 '14 at 11:09
1

You can do the following: instead of one set of the keys as static member, use a map mapping std::type_index to set of keys (or, if you cannot use C++11, std::type_info*). In each of your derived classes have a virtual function which returns the set of valid_keys for a class, and the validate function in the base class should get with typeid the type_info of the actual object, check if it already has the keys in the map - if not, the virtual function return the set is called, and the entry is added to the map.

Wojtek Surowka
  • 20,535
  • 4
  • 44
  • 51
0

Pass a reference to k_valid_keys in the constructor of your Validator classes and initialize a member reference. You'll skip construction for multiple Validator classes but you'll have to manage its lifetime.

You can then have one per inherited type if you want or not as well.

Using a register of k_valid_keys that is accessed by type or key could also work. Of course you would need to pass a reference to this register to your Validator classes.

Eric Fortin
  • 7,533
  • 2
  • 25
  • 33