Skip to content

Commit

Permalink
Effective java 추가
Browse files Browse the repository at this point in the history
  • Loading branch information
cheese10yun committed Jun 6, 2018
1 parent 987abcb commit bf03cbf
Show file tree
Hide file tree
Showing 4 changed files with 43 additions and 0 deletions.
Empty file added Effective-Java/03/Comparable.md
Empty file.
Empty file added Effective-Java/03/clone.md
Empty file.
33 changes: 33 additions & 0 deletions Effective-Java/03/hashCode.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
# equals를 재정의할 때는 반드시 hashCode도 재정의하라

* 많은 버그가 hashCode를 재정의하지 않아서 생긴다.
* **equals 메서드를 재정의한 클래스는 반드시 hashCode 메서드도 재정의햐아한다.**
* 그렇지 않으면 Obejct.hashCode의 일반 규약을 어기게 되므로, HashMap, HastSet, Hasttable 같은 Hash 기반 컬랙샨과 함께 사용된다면 오동작하게된다.

## Object 클래스 명세 일반 규약
* 으용프로그램 실행 중에 같은 객체의 hashCode를 여러 번 호출하는 경우, equals가 사용하는 정보들이 변경되지 않았다면, 언제나 동일한 정수가 리턴된다.(프로그램 종료시에는 같은 값이 나올 필요는 없다 )
* **equals(Object) 메서드가 같다고 판정한 두 객체의 hashCode 값은 같아야한다**
* equals(Object) 메서드가 다르다고 판정한 두 객체의 hashCode 값이 꼭 다를 필요는 없다. 그러나 서로 다른 hashCode 값이 나오면 해시 테이블의 성능이 향상될 수 있다는 점은 이해하고 있어야한다.

## 핵심 규약
* **hashCode 재정의하지 않으면 위반되는 핵심 규약은 두 번째다.같은 객체는 같은 해시 코드값을 가 져야한다는 규약이 위반되는 것이다.**
* hashCode를 재정의하지 않을 경우는 equals가 true임에도 서로다른 hashCode를 갖게된다.
* 따라서 Map 컬랙션에서 get메서드는 put 메서드가 객체를 저장한 것과 다른 해시버킷을 뒤지게된다.
* 설사 좋아서 같은 버킷을 뒤지게 되더라도 get 메서드는 항상 null을 리턴한다. HashMap은 성능 최적화를 위해 내부에 보관된 코드를 캐시해 두고, 캐시된 해시 코드가 없다면 객체는 동일성 검사조차 하지 않기 때문이다.
* 그렇다고 모든 객체가 같은 해시 코드를 갖게하는 방법으로 구현하면 안된다.
* 해시 테이블에서 검색하는 시간이 끔찍히 오래 걸리니가(뭐 당연한 이야기)
* 이상적인 해시; 함수는 서로 다른 객체들을 모든 가능한 해시에 값에 균등하게 분배햐야 한다.
* 이런 이상적인 해시 함수에 가까운 함수를 만드는 건 별로 어렵지 않다.
* 알맞는 자료형에 따라서 알고리즘이 달라진다. 결과적으로 나름 균등한 해쉬 값을 갖게하는거 같다.
* 내부적인 알고리즘은 좀 어렵다... 실용적인 방법은 아래 sample code 참조
* 주의할 것은, 성능 개선을하려고 객체의 중요 부분을 해시 코드 계산 과정에서 생략하면 안된다는 것이다.
* 해시 만드는 것에 로직이 있어 좀 오려 걸려도 해시 품질이 안좋아지면(값이 균등하지 않다면) 해시 기반으로 검색시 느려지기 때문에 결과적으로 더 느려진다는 내용


## Sample Code
```java
@Override
public int hashCode() {
return Objects.hash(id);
}
```
10 changes: 10 additions & 0 deletions Effective-Java/03/toString.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# 11 규칙 toString은 항상 재정의하라
* Object 클래스가 toString을 제공
* toString 규약 : 사람이 읽기 쉽도록 간략하지만 유용한 정보를 제공해야한다.
* @ + 16진수 표현된 해시코드가 붙은 문자열로 사람이 읽기 쉬운것은 아니다
* **그래서 모든 하위클래스에서 toString을 재정의함이 바람직하다.**
* toString을 재정의하지 않으면 진단 메시지를 통해서 얻을수 있는 저옵는 거의 없을 것이다.
* 가능하다면 toString 메서드는 객체 내의 중요 정보를 전부 담아 반한해야한다.
* equals, hashCode 규약을 따는 것보다는 덜 중요하다
* toSring 어떤 의도인지를 주석을 분명하게 남겨야한다
* toString을 통해서 필요한 비지니스 로직을 수행하기도 하니 말이다.

0 comments on commit bf03cbf

Please sign in to comment.