繁体   English   中英

C ++ getter / setter范例

[英]C++ getter/setter paradigm

我最近遇到了这个课程,并对如何实施吸气剂和制定者感到惊讶。

我以前没有碰到这个,并欢迎一些第二意见。

你认为这是一个很好的范例吗? 是坏事吗? 这是邪恶的吗?

标题:

    class Tool
{
public:
    Tool();
    virtual ~Tool();

    bool setName(const std::string &name);
    bool getName(std::string &name) const;

    void clearName();

private:
    std::string m_name;
    bool m_nameSet;

};

cpp文件:

#include "Tool.h"

Tool::Tool()
: m_name("")
, m_nameSet(false)
{
}


Tool::~Tool()
{
}


bool Tool::setName(const std::string &name)
{
    m_name = name;
    m_nameSet = true;
    return (m_nameSet);
}    

bool Tool::getName(std::string &name) const
{
    bool success = false;
    if (m_nameSet)
    {
        name = m_name;
        success = true;
    }
    return (success);
}

您选择getter的方式并不受欢迎,程序员更喜欢从getter return数据

std::string getName() const;

为什么应该在getter上重新检查之前设置或具有初始数据的项目? 如果要验证数据,请在setter上验证。

但是如果你坚持要将值返回为“之前设置的名称”,你可以通过bool isNameSet() const;写出第三种方法bool isNameSet() const;

这看起来很像C,通常返回状态代码以查看函数是否失败。

然后还有更好的方法来验证名称是否设置。 一个可能是对我使用boost :: optional这是一个更好的方法来声明可能不会始终设置名称的意图。

然而,我想知道通过只有一个构造函数将std :: string作为参数来确保名称始终设置并不是更好。

class Tool
{
public:
  //Constructor already does the right thing
  Tool() = default;
  virtual ~Tool();

  //Use void or return the modified class, akin to operators
  void setName(const std::string& name)
  {
    m_name = name;
  }
  //Alternatively
  Tool& setName(const std::string &name)
  {
    m_name = name;
    return *this;
  }

  //Return const reference to the value if possible, avoids copying if not needed
  //This will fail at run time if name is not set
  //Maybe throw an exception if that is preferred
  const std::string& getName() const
  {
    return *m_name;

    //Or

    if(m_name) return *m_name;
    else throw some_exception;
  }

  //Or return the optional, then calling code can check if name where set or not
  const boost::optional<std::string>& getName() const
  {
    return m_name;
  }


  void clearName()
  {
    m_name = boost::optional<std::string>();
  }

private:
  boost::optional<std::string> m_name;
};

我不会称之为范式 这似乎是架构的解决方案,其中一个字段可能处于未指定的状态(为什么不呢?有时它是一个理智的要求)。 虽然,我不太喜欢这个解决方案,因为getter应该返回值(对称,setter应该设置它),并且约定通常需要特定的原型:

Type GetValue();
SetValue (const Type & newValue);
or
SetValue (Type & newValue);
or
SetValue (Type newValue);

您应根据情况选择三个安装者中的一个,通常第一个或第二个适合。

如果一个领域可能处于未指定的状态,我会选择另一种方法,正如M M.在他的答案中建议的那样,我将自由提供一个例子:

class C
{
private:
    int field;
    bool fieldSet;

public:
    C()
    {
        field = 0;
        fieldSet = false;
    }

    bool IsFieldSet()
    {
        return fieldSet;
    }

    int GetField()
    {
        if (!fieldSet)
            throw std::exception("Attempt to use unset field!");

        return field;
    }

    void SetField(const int newValue)
    {
        field = newValue;
        fieldSet = true;
    }
};

但请注意,我不会这样称之为实施getter evil 使用它可能会让人感到不舒服。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM