2番目のオプションの方が魅力的ですが(コードが1行しかないため)、最初のオプションを選択します。
その理由は単にパフォーマンスです。小さなテストを実行した後、私はそれらの間に非常に大きな時間差を見つけました。
時間の概念を理解するために、次の2つの簡単なクラスを作成しました。
package equalsbuildertest;
import java.math.BigDecimal;
import java.util.Date;
import org.apache.commons.lang3.builder.EqualsBuilder;
import org.apache.commons.lang3.builder.HashCodeBuilder;
public class Class1 {
private int field1;
private boolean field2;
private BigDecimal field3;
private String field4;
private Date field5;
private long field6;
public Class1(int field1, boolean field2, BigDecimal field3, String field4,
Date field5, long field6) {
super();
this.field1 = field1;
this.field2 = field2;
this.field3 = field3;
this.field4 = field4;
this.field5 = field5;
this.field6 = field6;
}
public Class1() {
super();
}
public int getField1() {
return field1;
}
public void setField1(int field1) {
this.field1 = field1;
}
public boolean isField2() {
return field2;
}
public void setField2(boolean field2) {
this.field2 = field2;
}
public BigDecimal getField3() {
return field3;
}
public void setField3(BigDecimal field3) {
this.field3 = field3;
}
public String getField4() {
return field4;
}
public void setField4(String field4) {
this.field4 = field4;
}
public Date getField5() {
return field5;
}
public void setField5(Date field5) {
this.field5 = field5;
}
public long getField6() {
return field6;
}
public void setField6(long field6) {
this.field6 = field6;
}
@Override
public boolean equals(Object o) {
return EqualsBuilder.reflectionEquals(this, o);
}
@Override
public int hashCode() {
return HashCodeBuilder.reflectionHashCode(this);
}
}
と:
package equalsbuildertest;
import java.math.BigDecimal;
import java.util.Date;
import org.apache.commons.lang3.builder.EqualsBuilder;
import org.apache.commons.lang3.builder.HashCodeBuilder;
public class Class2 {
private int field1;
private boolean field2;
private BigDecimal field3;
private String field4;
private Date field5;
private long field6;
public Class2(int field1, boolean field2, BigDecimal field3, String field4,
Date field5, long field6) {
super();
this.field1 = field1;
this.field2 = field2;
this.field3 = field3;
this.field4 = field4;
this.field5 = field5;
this.field6 = field6;
}
public Class2() {
super();
}
public int getField1() {
return field1;
}
public void setField1(int field1) {
this.field1 = field1;
}
public boolean isField2() {
return field2;
}
public void setField2(boolean field2) {
this.field2 = field2;
}
public BigDecimal getField3() {
return field3;
}
public void setField3(BigDecimal field3) {
this.field3 = field3;
}
public String getField4() {
return field4;
}
public void setField4(String field4) {
this.field4 = field4;
}
public Date getField5() {
return field5;
}
public void setField5(Date field5) {
this.field5 = field5;
}
public long getField6() {
return field6;
}
public void setField6(long field6) {
this.field6 = field6;
}
@Override
public boolean equals(Object obj) {
if (!(obj instanceof Class2)) {
return false;
}
Class2 other = (Class2) obj;
EqualsBuilder builder = new EqualsBuilder();
builder.append(field1, other.field1);
builder.append(field2, other.field2);
builder.append(field3, other.field3);
builder.append(field4, other.field4);
builder.append(field5, other.field5);
builder.append(field6, other.field6);
return builder.isEquals();
}
@Override
public int hashCode() {
HashCodeBuilder builder = new HashCodeBuilder();
builder.append(getField1());
builder.append(isField2());
builder.append(getField3());
builder.append(getField4());
builder.append(getField5());
builder.append(getField6());
return builder.hashCode();
};
}
その2番目のクラスは、最初のクラスとほとんど同じですが、equalsとhashCodeが異なります。
その後、次のテストを作成しました。
package equalsbuildertest;
import static org.junit.Assert.*;
import java.math.BigDecimal;
import java.util.Date;
import org.junit.Test;
public class EqualsBuilderTest {
@Test
public void test1() {
Class1 class1a = new Class1(1, true, new BigDecimal(0), "String", new Date(), 1L);
Class1 class1b = new Class1(1, true, new BigDecimal(0), "String", new Date(), 1L);
for (int i = 0; i < 1000000; i++) {
assertEquals(class1a, class1b);
}
}
@Test
public void test2() {
Class2 class2a = new Class2(1, true, new BigDecimal(0), "String", new Date(), 1L);
Class2 class2b = new Class2(1, true, new BigDecimal(0), "String", new Date(), 1L);
for (int i = 0; i < 1000000; i++) {
assertEquals(class2a, class2b);
}
}
}
テストは非常に単純で、時間を測定するためだけに役立ちます。
結果は次のとおりです。
- test1(2,024秒)
- test2(0,039秒)
最高の時間を過ごすために、私はそれらを完全に等しくなるように選びました。NotEquals条件でテストを実行することを選択した場合、時間は短くなりますが、非常に大きな時間差も維持されます。
このテストは、Fedora21とEclipseLunaを搭載した64ビットIntelCore i5-3317U CPU @1.70GHzx4で実行します。
結論として、テンプレートを使用してとにかく入力できない可能性のある数行のコードを保存するために、パフォーマンスの大きな違いを危険にさらすことはありません(EclipseのWindows->設定はJava->エディター->テンプレートにあります)このような:
${:import(org.apache.commons.lang3.builder.HashCodeBuilder, org.apache.commons.lang3.builder.EqualsBuilder)}
@Override
public int hashCode() {
HashCodeBuilder hashCodeBuilder = new HashCodeBuilder();
hashCodeBuilder.append(${field1:field});
hashCodeBuilder.append(${field2:field});
hashCodeBuilder.append(${field3:field});
hashCodeBuilder.append(${field4:field});
hashCodeBuilder.append(${field5:field});
return hashCodeBuilder.toHashCode();
}
@Override
public boolean equals(Object obj) {
if (this == obj) {
return true;
}
if (obj == null) {
return false;
}
if (getClass() != obj.getClass()) {
return false;
}
${enclosing_type} rhs = (${enclosing_type}) obj;
EqualsBuilder equalsBuilder = new EqualsBuilder();
equalsBuilder.append(${field1}, rhs.${field1});
equalsBuilder.append(${field2}, rhs.${field2});
equalsBuilder.append(${field3}, rhs.${field3});
equalsBuilder.append(${field4}, rhs.${field4});
equalsBuilder.append(${field5}, rhs.${field5});${cursor}
return equalsBuilder.isEquals();
}