Design Pattern : VO ( Value Object ) μ μ¬μ©ν κΉ ?
μ½λλ€μ μ΄ν΄λ³΄λ€κ° VO κ° λ°κ²¬λλ€. μ΄κ²μ΄ 무μμΈκ³ .. νλ value object λλ€. μκ³ μμ΄μΌ ν κ² κ°λ€. DAO DTO VO impl ... μμ£Ό λͺ¨λ₯΄κ² λκ²λ€ ν¬μ±μ΄μ΄λ€. λμμΈν¨ν΄μ 곡λΆν΄μΌκ² λ€κ³ λ§μλ¨Ήμ μκ°μ΄μλ€. μκ²©μ¦ μν λ³Ό λ μμλ μμ² λ§μ λμμΈν¨ν΄λ€μ΄ μλ€λ μ¬μ€μ μμ§λ§ μΌλ¨ λ΄ μ 무μ λμμΈν¨ν΄μ μμμΌκ² λ€. μ΄μ°¨νΌ κ°λμλ λ°°μμ κΈλ°© μνμ§κΈ° λλ¬Έ..
1. VO( Value Obejct ) λ 무μμΌκΉ
VO μ κ·Έ μ¬μ μ μΈ μλ―Έλ μλμ κ°λ€.
VO(Value Object)λ κ°μ²΄μ§ν₯ νλ‘κ·Έλλ°μμ λ°μ΄ν°μ μΌκ΄μ±κ³Ό μ½λμ κ°λ μ±μ λμ΄κΈ° μν΄ μ¬μ©λλ μ€μν κ°λ μ λλ€. VOλ κ°λ³μ μΌλ‘ μλ³λ νμ μμ΄, κ·Έ λ΄λΆ κ°λ§μΌλ‘ μ μ λλ κ°μ²΄μ λλ€. μ¦, λ VO κ°μ²΄κ° κ°μ κ°μ κ°μ§λ©΄ λμΌν κ²μΌλ‘ μ·¨κΈλ©λλ€. μ΄λ¬ν νΉμ± λλΆμ VOλ λλ©μΈ λͺ¨λΈλ§μ΄λ λ°μ΄ν° μ λ¬ κ°μ²΄λ‘ λ리 μ¬μ©λ©λλ€.
λλ©μΈλͺ¨λΈλ§μ λκ³ λ°μ΄ν° μ λ¬ κ°μ²΄λ λκΉ. μ΄κ±΄ λ€μμ μμ보λλ‘ νκ³ , μμμΌ ν κ²μ
1. VOκ° λ°μ΄ν°μ μΌκ΄μ±κ³Ό μ½λμ κ°λ μ±μ λμΈλ€.
2. VOλ κ°λ³μ μΌλ‘ μλ³ λ νμ μμ΄, κ·Έ λ΄λΆ κ°λ§μΌλ‘ μ μ λλ κ°μ²΄μ΄λ€.
μ΄ λκ° μΈκ² κ°λ€. κ°λ³μ μΌλ‘ μλ³ λ νμ μμ΄ κ°μ κ°μ κ°μ§λ©΄ λμΌν κ²μΌλ‘ μ·¨κΈλλλ° μ΄κ²μ΄ μ΄λ»κ² (1) μ½λμ κ°λ μ±μ λμ΄λμ§λ μ¬μ€ μ μλΏμ§ μλλ€.
(2) μ μ μκ° λ΄λΆ κ°μ΄ κ°λ€κ³ κ°μ κ²μΌλ‘ μ·¨κΈλλ€. λΌλ μ€λͺ μμ λ§μΉμ§λ§, μ¬μ€ μ¬κΈ°μλ κ°λ³μ μΌλ‘ μλ³ λ νμ μλ€. κ° λ μ€μνλ€. μλ₯Όλ€μ΄ μ§μ‘면체λ₯Ό 그리기 μν΄
int sidelength_1
int sidelength_2
int sidelength_3
int sidelength_4
int sidelength_5
int sidelength_6
μ²λΌ primitive type μΌλ‘ νλμ© μ μΈνλ κ²μ΄ μλλΌ. κ·Έκ²μ μν κ°μ²΄λ₯Ό λ§λ€κ³ κ·Έ κ°μ²΄μ κ°μ΄ κ°λ€λ©΄ λμΌν κ²μΌλ‘ μ¬κΈ°κ² λ€λ μλ―Έμ΄λ€. κ°μ μν κ°μ²΄μΈ κ²μ΄λ€.
2. VO( Value Obejct ) μ μ°λκ±ΈκΉ ?
VO κ° μ¬μ©λλ μ΄μ λ primitive type μ΄ μ΄λ€ λλ©μΈμ κ°μ²΄λ₯Ό μ€λͺ νκΈ° λΆμ‘±νκΈ° λλ¬Έμ΄λ€.
μ¦, primitive type μΌλ‘ λ€κ°νμ λ§λ€κΈ° μν΄μλ μ§μ¬κ°νμ μν primitive type μ μμ±μ΄ νμνκ³ , μ μ€κ°νμ primitive type μμ±μ΄ νμνκ² λ κ² μ΄λ€. λ€κ°νμ λ§λ€κΈ° μν΄μ λ§€λ² λ³μλ₯Ό λ§λ€μ΄ μ€ κ²μΈκ° ? μ°λ¦¬λ κ°μ²΄λ₯Ό μκ³ μκΈ° λλ¬Έμ κ·Έλ΄νμκ° μλ€.
μ΄λ° κ°λ¨ν μ¬λ‘μ²λΌ VO κ° primitive type λ³΄λ€ μ μ°μΈλ€λ μ¦ νμνλ€λ κ²μ μ΄ν΄λ³΄μ.
2.1 ) primitive type μ κ°μ²΄κ° μ λλ‘ νμ©νμ§ μλλ€.
public class Ladder {
private final int width;
private final int height;
public void Ladder(int width, int height) {
this.width = width;
this.height = height;
}
}
μ΄λ Ladder μμ±μ μΈμλ int λ₯Ό μ¬μ©νμ§λ§, μ§μ§ Ladder κ°μ²΄κ° width μ heigth λ₯Ό μ μ¬μ©νμκΉ ?
μλλ€. κ·Έ μ΄μ λ μλ£νμ μμ±μ μ λλ‘ κ³ λ €νμ§ μμκ²μ΄κΈ° λλ¬Έμ΄λ€. λ¨μ μΌλ‘
1. μ¬λ€λ¦¬μ λμ΄κ° λν΄μ§λ κΈ°λ₯μ΄ νμνκ° ?
2. μ¬λ€λ¦¬μ λμ΄λ₯Ό κ³±νκ±°λ λλλ κ²μ΄ κ°λ₯νκ°?
3. μ¬λ€λ¦¬μ λμ΄κ° μμκ° λλκ²μ΄ κ°λ₯νκ°?
μ μ§λ¬Έμμ "μ"λ μλ€. integer λ μμ μ°μ°μ΄ κ°λ₯ν μλ£νμΈλ° μ integer λ₯Ό νμ©ν΄μΌ ν κΉ ? μ΄ μ μ΄ κ°μ²΄κ° primitive λ₯Ό μ λλ‘ νμ©νμ§ μλλ€λ κ²μ΄λ€.
μ΄λ κ² λ³ μκ°μμ΄ λλ©μΈμ μμ±μ λνλ΄κΈ° μν΄μ primitive type μ μ°λ κ΄μ΅μ primitive obsessionμ΄λΌκ³ νλ€.
[μ°Έμ‘°] https://ksh-coding.tistory.com/83
VO(Value Object)λ 무μμΌκΉ? μ μ¬μ©ν κΉ?
1. VO(Value Object)λ? VOμ μλ―Έλ₯Ό 보면 λ€μκ³Ό κ°λ€. * VOλ λλ©μΈμμ ν κ° λλ κ·Έ μ΄μμ μμ±λ€μ λ¬Άμ΄μ νΉμ κ°μ λνλ΄λ κ°μ²΄λ₯Ό μλ―Ένλ€. * ν΄λΉ μμ±λ€μ primitive νμ μ΄λ€! (int, boolean, ...
ksh-coding.tistory.com
2.2 ) ν κ³³μ΄ μλλΌ μ¬λ¬κ³³μμ μ¬μ©λ λ μ€λ³΅ μ½λκ° λ°μνλ€.
λλΉμ λμ΄λ₯Ό κ°μ§λ κ²μ΄ μ¬λ€λ¦¬ λΏ μλλΌ μ§μ¬κ°ν λνλ κ°μ§ μ μλ€. μ΄λ μ¬λ€λ¦¬μ μ§μ¬κ°νμ λλΉμ λμ΄μ λν μ ν¨μ±μ κ²μ¬ν νμ μμ±λμ΄μΌ νλ€. κ·Έλ κΈ° λλ¬Έμ μ§μ¬κ°νκ³Ό μ¬λ€λ¦¬ μ²λΌ λμ΄μ λμ΄μ μμ±μ κ°μ§λ λͺ¨λ κ°μ²΄μ μ€λ³΅λλ μ½λκ° λ°μ ν κ²μ΄λ€.
κ·Έλμ λμ΄μ λλΉκ° μ λλ‘ μ¬μ©λμ΄ ν€λ©μ§ μλλ‘ μ€κ³λ₯Ό ν΄μΌ ν κ²μ΄λ€.
2.3 ) ν κ³³μ΄ μλλΌ μ¬λ¬ κ³³μμ μ¬μ©λ λ λΆλ³μ ν λ²μ 보μ₯ν μ μλ€.
2-2 μ λ§μ°¬κ°μ§λ‘ λλΉμ λμ΄λ₯Ό κ°μ§λ κ²μ΄ μ¬λ€λ¦¬ λΏ μλλΌ λ€λ₯Έ λνμ κ°μ²΄λ κ°μ§ μ μλλ°, μ΄ λλ¬Έμ λ΄κ° λ§μ§λ§μΌλ‘ μ κ·Όνλ κ°μ²΄μ λλΉκ° μ§μ¬κ°νμΈμ§ μ¬λ€λ¦¬κΌ΄μΈμ§ 보μ¦ν μ μλ? μλ€. μ΄κ²μ μν΄μλ κ° κ°μ²΄ μ μΈ λ¨κ³μμ final μ΄ λΆμλμ§ νμΈν΄μΌνλ€ κ·Έλ§μ λ μμΌλ©΄ λ΄κ° μ΄λ€ λλΉμ μ κ·Όνλμ§ μ μ μκ² λλ€. λ°λΌμ VO λ₯Ό ν΅ν΄ μ΄ λ¬Έμ μ λ€μ μ μ ν μ€κ³λ‘ ν΄κ²°νλ €λ κ²μ΄λ€.
β VO κ° μ§μ§λ‘ μ¬μ©λλ μ΄μ
1. primitive νμ μ κΈ°λ₯λ€μ 'κ°'μ΄ λ€ μ¬μ©νμ§ μλλ€.
2. 'κ°'μ΄ μ¬λ¬ κ³³μμ μ¬μ©λλ©΄ μ λ³΄κ° λͺ¨λ μ¬λ¬ κ³³μ νΌμ Έ μκΈ° λλ¬Έμ, μ ν¨μ± κ²μ¬λ λΆλ³ μ²΄ν¬ λ±μ ν΄λΉ 'κ°'μ΄ μλ λͺ¨λ κ°μ²΄μμ μ§νν΄μΌνλ€.
3. VO( Value Obejct ) μμ± μ μ½μ‘°κ±΄/νΉμ§
1. λΆλ³μ± (Immutability)
VOλ μΌλ°μ μΌλ‘ λΆλ³μ±μ κ°μ§λ©°, ν λ² μμ±λ ν κ·Έ κ°μ΄ λ³κ²½λμ§ μλλ€. λΆλ³μ±μ ν΅ν΄ λ°μ΄ν°μ μΌκ΄μ±μ 보μ₯νκ³ , λ°μ΄ν°κ° μκΈ°μΉ μκ² λ³κ²½λλ λ¬Έμ λ₯Ό λ°©μ§ν μ μλ€.μλ₯Ό λ€μ΄, MoneyλΌλ VO κ°μ²΄κ° μμ λ, amountμ currencyλΌλ κ°μ΄ μ΄κΈ°νλ μ΄νμλ λ³κ²½λμ§ μλκ²μ΄γ γ·.
2. λλ±μ±_κ°μΌλ‘λΉκ΅λ (Equality by Value)
VOλ λμΌν κ°μ κ°μ§λ κ²½μ° λμΌν κ°μ²΄λ‘ κ°μ£Όλ©λλ€. μ΄λ‘ μΈν΄ VOλ λ©λͺ¨λ¦¬ μ£Όμκ° μλλΌ κ°μ²΄κ° κ°μ§ κ°μ λ°λΌ λμΌμ±μ νλ¨νκ² λ©λλ€. μλ₯Ό λ€μ΄, λ Address κ°μ²΄κ° street, city, state, postalCodeκ° λͺ¨λ κ°λ€λ©΄ λμΌν κ°μ²΄λ‘ μΈμλ©λλ€.
3. μκ° μ ν¨μ± κ²μ¬ (Self -Validation)
primitive type μ μ¬μ© νμ λ μ¬μ© ν λͺ¨λ κ³³μμ μ ν¨μ± κ²μ¬λ₯Ό ν΄μΌνλ€λ λ¬Έμ μ μ΄ μμλ€. VO λ₯Ό μ¬μ©νλ€λ©΄ 격리λ κ°μ²΄ μμμ μ ν¨μ±μ κ²μ¬νμ¬ μ¬μ© ν μ μλ€.
4. VO( Value Obejct ) μ¬μ© μμ
μμ λλΉμ λμ΄μ μ¬λ€λ¦¬λ‘ VO λ₯Ό μ€λͺ νλλ°, primitive type μ΄ μλ VO νΉμ±μ μ§μΌμ λ§λ€μ΄λ³΄λ©΄ μλμ κ°λ€.
public class ShapeProperty {
// λΆλ³μ± (Immutable)
private final int width;
private final int height;
public Shape(final int width, final int height) {
// μκ° μ ν¨μ± κ²μ¬ (Self-Validation)
validateWidth(width);
validateHeight(height);
this.width = width;
this.height = height;
}
// λλ±μ± (Equality)
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
ShapeProperty that = (ShapeProperty) o;
return width == that.width && height == that.height;
}
@Override
public int hashCode() {
return Objects.hash(width, height);
}
}
VO λ₯Ό ν΅ν΄μ width μ height λ₯Ό μ¬μ© ν μλ μλ κ°μ²΄μλ ShapeProperty κ°μ²΄λ₯Ό μ¬μ©ν΄ κ·Έ κ°μ 보μ₯νλ κ²μ΄λ€. μλλ VO λ₯Ό νμ©ν΄ μ¬λ€λ¦¬λ₯Ό μ μΈν κ²μ΄λ€.
// μμ νμ
μ¬μ©
public class Ladder {
private final int width;
private final int height;
public void Ladder(int width, int height) {
validateWidth(width);
validateHeight(height);
this.width = width;
this.height = height;
}
}
// VOλ‘ λ³κ²½
public class Ladder {
private final ShapeProperty shapeProperty;
public void Ladder(final ShapeProperty shapeProperty) {
this.shapeProperty = shapeProperty;
}
}
λ.