- 无ID属性
- 判断相等的方法只能是抽象方法
值对象没有ID属性,也就没有对应字段,这意味着我们没办法在基类中判断两个值对象是否相等。为了判断其结构相等,我们可以在基类中构建基础方法:
package com.lugew.springbootddd;/*** @author 夏露桂* @since 2021/6/8 17:40*/public abstract class ValueObject<T> {@Overridepublic boolean equals(Object obj) {T valueObject = (T) obj;if (valueObject == null)return false;return equalsCore(valueObject);}@Overridepublic int hashCode() {return getHashCodeCore();}protected abstract boolean equalsCore(T other);protected abstract int getHashCodeCore();}
可以看到我们重写了equals和hashCode方法,并且将具体的实现委托给了其子类。此时,我们可以将Money类进行重构:
package com.lugew.springbootddd.snackmachine;import com.lugew.springbootddd.ValueObject;/*** @author 夏露桂* @since 2021/6/7 11:59*/public class Money extends ValueObject<Money> {private final int oneCentCount;private final int tenCentCount;private final int quarterCount;private final int oneDollarCount;private final int fiveDollarCount;private final int twentyDollarCount;public Money(int oneCentCount, int tenCentCount, int quarterCount, intoneDollarCount, int fiveDollarCount, int twentyDollarCount) {this.oneCentCount = oneCentCount;this.tenCentCount = tenCentCount;this.quarterCount = quarterCount;this.oneDollarCount = oneDollarCount;this.fiveDollarCount = fiveDollarCount;this.twentyDollarCount = twentyDollarCount;}public static Money add(Money money1, Money money2) {return new Money(money1.oneCentCount + money2.oneCentCount,money1.tenCentCount + money2.tenCentCount,money1.quarterCount + money2.quarterCount,money1.oneDollarCount + money2.oneDollarCount,money1.fiveDollarCount + money2.fiveDollarCount,money1.twentyDollarCount + money2.twentyDollarCount);}@Overrideprotected boolean equalsCore(Money other) {return oneCentCount == other.oneCentCount&& tenCentCount == other.tenCentCount&& quarterCount == other.quarterCount&& oneDollarCount == other.oneDollarCount&& fiveDollarCount == other.fiveDollarCount&& twentyDollarCount == other.twentyDollarCount;}@Overrideprotected int getHashCodeCore() {int hashCode = oneCentCount;hashCode = (hashCode * 397) ^ tenCentCount;hashCode = (hashCode * 397) ^ quarterCount;hashCode = (hashCode * 397) ^ oneDollarCount;hashCode = (hashCode * 397) ^ fiveDollarCount;hashCode = (hashCode * 397) ^ twentyDollarCount;return hashCode;}}
父类的抽象方法equalsCore,getHashCodeCore子类是必须实现的。equalsCore根据每个字段的值来判断两个值对象是否相等。
在这里,我再次重申实体和值对象的区别:实体ID相等而值对象结构相等,值对象不存在ID字段。
