我将尝试总结这里已经给出的一些我同意的观点。
我个人认为没有“感觉更好”的答案。 确实存在为什么您不希望实用程序类填充静态方法的正当理由。
简短的回答是,在面向对象的世界中,您应该使用对象以及它们附带的所有好“东西”(封装、多态)
多态性
如果计算基因之间距离的方法变化,您应该大致(更可能是Strategy)每个变异都有一个基因类。封装变化的东西。否则你会得到多个 if。
这意味着,如果出现计算基因间距离的新方法,您不应修改现有代码,而应添加新代码。否则你可能会破坏已经存在的东西。
在这种情况下你应该添加一个新的基因类,而不是修改写在#geneDistance
中的代码
您应该告诉您的对象该做什么,而不是询问他们的状态并为他们做出决定。突然间你打破了single responsibility principle,因为那是多态性。
可测试性
静态方法可能很容易单独测试,但以后您将在其他类中使用此静态方法。在隔离测试这些类时,您将很难做到。或者更确切地说不是。
我会让Misko 说出他的说法,这可能比我想出的要好。
import junit.framework.Assert;
import org.junit.Test;
public class GeneTest
{
public static abstract class Gene
{
public abstract int geneDistance(Gene other);
}
public static class GeneUtils
{
public static int geneDistance(Gene g0, Gene g1)
{
if( g0.equals(polymorphicGene) )
return g0.geneDistance(g1);
else if( g0.equals(oneDistanceGene) )
return 1;
else if( g0.equals(dummyGene) )
return -1;
else
return 0;
}
}
private static Gene polymorphicGene = new Gene()
{
@Override
public int geneDistance(Gene other) {
return other.geneDistance(other);
}
};
private static Gene zeroDistanceGene = new Gene()
{
@Override
public int geneDistance(Gene other) {
return 0;
}
};
private static Gene oneDistanceGene = new Gene()
{
@Override
public int geneDistance(Gene other) {
return 1;
}
};
private static Gene hardToTestOnIsolationGene = new Gene()
{
@Override
public int geneDistance(Gene other) {
return GeneUtils.geneDistance(this, other);
}
};
private static Gene dummyGene = new Gene()
{
@Override
public int geneDistance(Gene other) {
return -1;
}
};
@Test
public void testPolymorphism()
{
Assert.assertEquals(0, polymorphicGene.geneDistance(zeroDistanceGene));
Assert.assertEquals(1, polymorphicGene.geneDistance(oneDistanceGene));
Assert.assertEquals(-1, polymorphicGene.geneDistance(dummyGene));
}
@Test
public void testTestability()
{
Assert.assertEquals(0, hardToTestOnIsolationGene.geneDistance(dummyGene));
Assert.assertEquals(-1, polymorphicGene.geneDistance(dummyGene));
}
@Test
public void testOpenForExtensionClosedForModification()
{
Assert.assertEquals(0, GeneUtils.geneDistance(polymorphicGene, zeroDistanceGene));
Assert.assertEquals(1, GeneUtils.geneDistance(oneDistanceGene, null));
Assert.assertEquals(-1, GeneUtils.geneDistance(dummyGene, null));
}
}