多态 - 对象变量

时间:2013-05-24 20:52:31

标签: c++ polymorphism

我有一个类CTag,用于检查HTML标记属性的有效性。

class CTag {
  vector<string> m_attr; // list of attributes
  string m_tag;
 public:
  void CheckAttr (); // go through the vector and search for valid attributes
};

class CDiv : public CTag {

 public:
  CDiv( const string & tag ) {
    string attr[] = {"id","class"};
    /* I would like to save string and array to the main class :

    int size = sizeof(attr) / sizeof(string);
    m_attr.assign(attr,attr+size);
    m_tag = tag;

    but I can't because they are private
    */
  }
};

和另一个标签类......

在main中:

CDiv a("<div class=\"haha\">);
CDiv b("<div hello=\"haha\">"); // wrong attribute

解析字符串并搜索有效属性时没有问题。我只是不确定如何保存这些数据。我应该制作一个setter方法吗?或者我可以公开这些变量吗?

感谢您的帮助。

3 个答案:

答案 0 :(得分:0)

使用关键字protected

class CTag {
 protected:
 ^^^^^^^^^^

  vector<string> m_attr; // list of attributes
  string m_tag;

 public:
  ...
};

默认访问权限为private,包含私有部分的项目对于儿童而言是私有的。如果您使用protectd,孩子们可以访问它们。

更好的做法是使用setter / getter:

class CTag {
  vector<string> m_attr; // list of attributes
  string m_tag;

 protected:
  void setTag(const string &tag)
  {
    m_tag = tag;
  }

 public:
  ...
};

现在,孩子可以按setTag设置标记。

答案 1 :(得分:0)

您可以使它们protected,这将使这些数据成员对派生类可见。或者您可以保留成员private并提供protected设置者(可能还有protected获取者)。

    class CTag {
    public:
        void CheckAttr ();
    protected:
//  ^^^^^^^^^^
        void set_tag(std::string s)
        {
             m_tag = std::move(s);
        }
        void set_attributes(std::vector<string> attrs)
        {
             m_attr = std::move(attrs);
        }
    private:
        vector<string> m_attr; // list of attributes
        string m_tag;
    };

受保护的成员 无法访问&#34;来自外部&#34; CTag类的private类,与private成员类似,但与{{1}}成员不同,可以从派生类中访问它们。

答案 2 :(得分:0)

我的方法看起来像这样:

class CTag
{
public:
  CTag(string const &tag_)
   : m_tag(tag_) {}
  void CheckAttr();
protected:
  virtual vector<string> const &Attributes() const = 0;
private:
  string m_tag;
};

class CDiv : public CTag
{
public:
  CDiv(string const &tag_) : CTag(tag_)
  { if (m_vec_attr.empty()) m_vec_attr.assign(m_attrs.begin(), m_attrs.end()); }
protected:
  virtual vector<string> const &Attributes() const { return m_vec_attr; }
private:
  static vector<string> m_vec_attr;
  static std::tr1::array<string, 2> m_attrs;
     // the '2' needs to match the number of attrs, kind of a pain
};
std::tr1::array<string,2> CDiv::m_attrs = {"id","class"};
vector<string> CDiv::m_vec_attr;

初始化一个简单类型的问题通过在构造函数中向下传递来显示;这是初始化成员的首选方法。

如果您不使用C ++ 11,则数组/向量fu是由于难以初始化向量。如果你是,那么抛弃数组,不要打扰构造函数初始化或转换,只需初始化静态向量。实际上,如果你是,你可以将CDiv构造函数中的文字{ "id", "class" }参数传递给CTag构造函数;我没有触手可及的编译器来测试它。