Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

typeid.name returns a number before the derived class type

I have these classes: (class Question is abstract the others are derived)

class Question{
};

class QSingleChoice{
};

class QMultipleChoice{
};

etc.

I have a vector<Question*> that stores multiple question types. In the GUI I need to know what type of question I have to show, so I'm using string questionType = typeid(*question).name() but instead of "QSingleChoice", "QMultipleChoice" etc. it returns "13QSingleChoice", "5QText", "9QOrdering" etc. What are those numbers? And can I suppose that they will be always the same or it's possible that when I run the program on a different computer, the typeid returns somethin like "19QSingleChoice" or something completely different like "ASDQSingleChoice"?

like image 948
skluzada Avatar asked May 26 '18 15:05

skluzada


1 Answers

The name returned by std::type_info::name is implementation-defined, which means it's fully up to each compiler to decide how it wants to represent names of types. In other words, this is not something you could rely on. It's useful for debugging, and can be used for some comparisons within the same run of the program, but I wouldn't consider it usable for much more than that: you'd have to inspect your compiler's documentation to figure out if it offers the guarentees you need.

It's generally much better to introduce such functionality yourself if you need it, perhaps in the form of a virtual const std::string& classId() const;.

It could be implemented like this:

class Question {
public:
  virtual const std::string& getClassId() const = 0;
};

class QSingleChoice : public Question {
public:
  const std::string& getClassId() const override
  {
    static const std::string name{"SingleChoice"};
    return name;
  }
};


class QMultipleChoice : public Question {
public:
  const std::string& getClassId() const override
  {
    static const std::string name{"MultipleChoice"};
    return name;
  }
};

Alternatively, you can create and return an enumeration instead of a string name.

However, first make sure that you actually need it in the first place. Quite often, the need to inspect and identify a particular type hiding behind an abstract interface indicates bad design. If the GUI is an integral part of the program, perhaps Question could simply offer virtual functions such as virtual void display() const;. Alternatively, if the GUI is largely external to the questions, perhaps using the visitor pattern might be more appropriate.

like image 182
Angew is no longer proud of SO Avatar answered Oct 20 '22 14:10

Angew is no longer proud of SO