让二传手返回布尔值是好习惯吗?

Is it good practice to have a setter return a bool?

本文关键字:好习惯 布尔值 二传手 返回      更新时间:2023-10-16

例如,考虑以下两个二传手:

bool setMonth(int month) {
    bool valid = false;
    if (month > 0 && month < 12) {
        this->month = month;
        valid = true;
    }
    return valid;
}

void setMonth(int month) {
   if (month > 0 && month < 12) {
      this->month = month;
   }
}

第一个让类的客户端显式知道集合是否失败。这算不算好做法?

我不这么认为。这意味着无论何时设置某些内容,都必须检查操作是否成功。
我认为提出异常会是一个更好的主意,因为可读性和逻辑性。
我发现:

/*program stuff*/
try{
    YourObject.setMonth(0);
    /* other stuff*/
}catch YourException{
/* recovery*/
}

更清洁的是:

/*program stuff*/
if(!YourObject.setMonth(0)){
    /*recovery*/
}else{
    /*stuff*/
}

在逻辑(我会说哲学(和可读性方面。

有人

可能会争辩说,使用boolean作为返回类型并没有什么坏处。在最坏的情况下,您只是忽略检查。

另一个人可能会争辩说,抛出异常也更优雅,信息量更大(如Java的IllegalArgumentException或Python的ValueError(,但这可能会导致更多的"麻烦",因为异常必须以一种或另一种方式从客户端代码中处理。

如果您需要确保插入的值绝对正确,第三种方法是将允许的值封装在结构实体(如类、枚举或命名空间(中。
Java 中的一个例子是:

public void setMonth(Month month){
    this.month = month;     // member month is now of type Month
}

public enum Month{
    JANUARY(1),
    FEBRUARY(2),
    MARCH(3),
    APRIL(4),
    MAY(5),
    JUNE(6),
    JULY(7),
    AUGUST(8),
    SEPTEMBER(9),
    OCTOBER(10),
    NOVEMBER(11),
    DECEMBER(12)

    private int n;
    private Month(int n){
        this.n = n;
    }
}

使用方式是:

someObject.setMonth(Month.FEBRUARY);

(您可以使用 C++ 中的命名空间实现相同的操作。

当您想要跟踪插入到它们的无效数据时,最好在 setter 中使用异常。在这种情况下,方法的签名是:

//throw exception when month is out of range 
    void setMonth(int month) throws InvalidMonthNumberException;

如果您想在月份超出范围时设置默认数据,请在 javadoc 中描述。

/*
* If month < 1 or month > 12 default month (1) accepted
*/
void setMonth(int month);

如果是java(你标记了两种语言(,那么最佳实践是从setter返回void。如果设置值失败,则抛出异常。对于您的情况,您应该抛出IllegalArgumentException月份设置器。