我正在设计一个新的服务,该服务需要两个字符串,并且可以更改它们,也可以不更改并返回(可能)修改后的值。

例如:

public class Phrases
{
    public string Phrase1 { get; set; }
    public string Phrase2 { get; set; }
}

public interface IModifier
{
    Phrases Go(Phrases phrases);
}


此外,客户应知道原始搜索词是否已更改。

问题是:返回的类型应该是什么?

如果是相同的Phrases类,则==运算符(和/或Equals方法)应该有一个重载。这样客户端的代码将如下所示:

Phrases phrases = new Phrases { Phrase1 = "hello", Phrase2 = "world" };
Phrases modifierResult = someModifier.Go(phrases);
if (modifierResult.Equals(phrases))
    // do something
    ;


但是,这也使客户端也保持原始状态。

另一种方法是在修饰符结果的返回类型中包含一个额外的字段:

public interface IModifier
{
    ModifiedPhrases Go(Phrases phrases);
}

public class ModifiedPhrases : Phrases
{
    public bool IsModified { get; set; }
}


然后,客户端将具有IsModified字段,而无需保留原始实例。
但是,这样,我们在系统中就有另一种类型。此外,也许一开始就指示修改不是服务的责任。因此,检查修改可能是客户的责任,因此IsModified可能是不必要的。

您会选择什么,为什么?

最佳答案

您的两个建议听起来都不错,我的选择将取决于具体情况,主要是我必须保持多少个原始状态多长时间,以及我必须进行多少次平等检查。从设计的角度来看,我更喜欢使用方法IsModified



一些细节:

如果您不使用isModified:请考虑使Phrases不可变,例如在Java中通过

public class Phrases
{
    private String phrase1;
    private String phrase2;

    public Phrases(String p1, String p2) {
      phrase1 = p1;
      phrase2 = p2;
    }

    //getter and no setter for phrase1 and phrase2...

    //equals()...
}


然后,您可以选择使构造函数私有化,并提供具有缓存功能的工厂方法,甚至可以保证仅存在一个包含{“ hello”,“ world”}的实例。这样,您可以节省内存,并可以通过检查对象标识来更快地进行相等性检查。

如果使用的是isModified:考虑使用枚举而不是boolean IsModified。这样,您可以按照Gregory的建议扩展对象可能处于的状态,但是使用的方式要简洁得多。有关详细信息,请参见Josh Bloch's Effective Java项目30,“使用枚举代替int常量”。

10-06 05:29