Fault
Fault

Reputation: 420

Polymorphism: accessing static members via class literal or object

Suppose you need to access a member of a struct/class either via the class literal, or through an inherited object of that class. It might looks something like this:

struct Component {
    static const long key = 0;
    virtual long getKey() {return key;};
};

struct FooComponent : Component {
    static const long key = 0x1;
    virtual long getKey() {return key;};
};

struct BarComponent : Component {
    static const long key = 0x2;
    virtual long getKey() {return key;};
};

With the above, key can be accessed either via:

long key = FooComponent::key;

or

FooComponent foo;
long key = foo.getKey();

Now my question is: is there some cleaner, less redundant way of achieving the above? Ideally virtual long getKey() {return key;}; would only need to be specified once, not for every inherited class.

EDIT:

Class hierarchy is important. The components are stored in a single container, in my case an unordered_map:

std::unordered_map<long, std::unique_ptr<Component>> components;

Upvotes: 1

Views: 73

Answers (2)

Sam Cristall
Sam Cristall

Reputation: 4387

Extending @iavr's answer to the new requirements:

struct Component {
  virtual ~Component() {}
  virtual long getKey() { return 0; }
};

template <int Key>
struct KeyedComponent : Component {
  long getKey() { return Key; };
};

struct FooComponent : KeyedComponent<1> { };
struct BarComponent : KeyedComponent<2> { };

Tested with:

std::vector<std::unique_ptr<Component>> components;
components.emplace_back(new FooComponent());
components.emplace_back(new BarComponent());

for (auto& component : components) {
  std::cout << component->getKey() << std::endl;
}

Prints:

1
2

Upvotes: 2

iavr
iavr

Reputation: 7637

Static polymorphism is your friend here:

template <long K = 0>
struct Component {
    static constexpr long key = K;
    long getKey() {return key;};
};

struct FooComponent : Component <0x1> {};

struct BarComponent : Component <0x2> {};

Upvotes: 2

Related Questions