diff --git "a/Ch09/item68/\354\235\274\353\260\230\354\240\201\354\234\274\353\241\234_\355\206\265\354\232\251\353\220\230\353\212\224_\353\252\205\353\252\205_\352\267\234\354\271\231\354\235\204_\353\224\260\353\245\264\353\235\274.md" "b/Ch09/item68/\354\235\274\353\260\230\354\240\201\354\234\274\353\241\234_\355\206\265\354\232\251\353\220\230\353\212\224_\353\252\205\353\252\205_\352\267\234\354\271\231\354\235\204_\353\224\260\353\245\264\353\235\274.md" new file mode 100644 index 0000000..bbb9614 --- /dev/null +++ "b/Ch09/item68/\354\235\274\353\260\230\354\240\201\354\234\274\353\241\234_\355\206\265\354\232\251\353\220\230\353\212\224_\353\252\205\353\252\205_\352\267\234\354\271\231\354\235\204_\353\224\260\353\245\264\353\235\274.md" @@ -0,0 +1,67 @@ +## 🌱 철자 κ·œμΉ™ +### ☁️ νŒ¨ν‚€μ§€μ™€ λͺ¨λ“ˆ 이름 +각 μš”μ†Œλ₯Ό `.` 으둜 κ΅¬λΆ„ν•˜μ—¬ **계측적**으둜 μ§“λŠ”λ‹€. +λ§Œμ•½ 쑰직 λ°”κΉ₯μ—μ„œλ„ μ‚¬μš©λ  νŒ¨ν‚€μ§€λΌλ©΄, 쑰직의 인터넷 도메인 이름을 μ—­μˆœμœΌλ‘œ μ‚¬μš©ν•˜λ©΄ λœλ‹€. ex) `com.google` + +각 νŒ¨ν‚€μ§€ 이름은 μ†Œλ¬Έμžλ₯Ό μ‚¬μš©ν•œ 8자 μ΄ν•˜μ˜ 짧은 단어 ν˜Ήμ€ **μ•½μ–΄**λ₯Ό μΆ”μ²œν•œλ‹€. +`utilities` λ³΄λ‹€λŠ” `util` 이 μ’‹λ‹€. + +### ☁️ ν΄λž˜μŠ€μ™€ μΈν„°νŽ˜μ΄μŠ€ 이름 +ν•˜λ‚˜ μ΄μƒμ˜ λ‹¨μ–΄λ‘œ 이루어지며, 각 λ‹¨μ–΄λŠ” λŒ€λ¬Έμžλ‘œ μ‹œμž‘ν•΄μ•Ό ν•œλ‹€ +λ‹¨μ–΄μ˜ 첫 κΈ€μžλ§Œ λ”΄ μ•½μžλ‚˜ `max`, `min` 처럼 널리 ν†΅μš©λ˜λŠ” μ€„μž„λ§μ„ μ œμ™Έν•˜κ³  단어λ₯Ό 쀄여 μ“°λ©΄ μ•ˆλœλ‹€. + +### ☁️ λ©”μ„œλ“œμ™€ ν•„λ“œ 이름 +첫 κΈ€μžλ₯Ό μ†Œλ¬Έμžλ‘œ μ“΄λ‹€λŠ” 점만 λΉΌλ©΄ 클래슀 λͺ…λͺ… κ·œμΉ™κ³Ό κ°™λ‹€. λ§Œμ•½ 첫 단어가 μ•½μžλΌλ©΄, 단어 전체가 μ†Œλ¬Έμžμ—¬μ•Ό ν•œλ‹€. + +#### πŸ”– μƒμˆ˜ ν•„λ“œ +단, μƒμˆ˜ ν•„λ“œλŠ” μ˜ˆμ™Έμ μœΌλ‘œ λͺ¨λ‘ **λŒ€λ¬Έμž**둜 μ“°λ©° 단어 μ‚¬μ΄λŠ” λ°‘μ€„λ‘œ κ΅¬λΆ„ν•œλ‹€. +```java +private static final int NEGATIVE_INFINITY = XX +``` +μ£Όμ˜ν•  점은 `static final` ν•„λ“œμ΄λ©΄μ„œ, κ°€λ¦¬ν‚€λŠ” 객체가 λΆˆλ³€μ΄λΌλ©΄ 비둝 κ·Έ νƒ€μž…μ€ 가변이더라도 μƒμˆ˜ ν•„λ“œλΌλŠ” 것이닀. 즉, `static final` νƒ€μž…μ΄ **κΈ°λ³Έ νƒ€μž…μ΄λ‚˜ λΆˆλ³€ μ°Έμ‘° νƒ€μž…**이라면 μƒμˆ˜ ν•„λ“œμ— ν•΄λ‹Ήν•œλ‹€. + +### ☁️ νƒ€μž… λ§€κ°œλ³€μˆ˜ +νƒ€μž… λ§€κ°œλ³€μˆ˜μ˜ 이름은 보톡 ν•œ 문자둜 ν¬ν•¨ν•œλ‹€. +> +`T` : μž„μ˜μ˜ νƒ€μž… +`E` : μ»¬λ ‰μ…˜ μ›μ†Œμ˜ νƒ€μž… +`K`, `V`: 맡의 킀와 κ°’ +`X` : μ˜ˆμ™Έ +`R` : λ©”μ„œλ“œ λ°˜ν™˜ νƒ€μž… +`T`, `U`, `V` (`T1`, `T2`, `T3`) : μž„μ˜ νƒ€μž…μ˜ μ‹œν€€μŠ€ + +## 🌱 문법 κ·œμΉ™ +### ☁️ 클래슀 + +보톡 **λ‹¨μˆ˜ λͺ…μ‚¬λ‚˜ λͺ…사ꡬ**λ₯Ό μ‚¬μš©ν•œλ‹€. + +1. 객체λ₯Ό 생성할 수 μ—†λŠ” 클래슀의 이름은 보톡 λ³΅μˆ˜ν˜• λͺ…μ‚¬λ‘œ μ§“λŠ”λ‹€.(ex) `Collectors` ) +2. μΈν„°νŽ˜μ΄μŠ€ 이름은 ν΄λž˜μŠ€μ™€ λ˜‘κ°™κ±°λ‚˜ `able` ν˜Ήμ€ `ible` 둜 λλ‚˜λŠ” ν˜•μš©μ‚¬λ‘œ μ§“λŠ”λ‹€. (ex) `Runnable`, `Accessible`) +3. μ• λ„ˆν…Œμ΄μ…˜μ€ λͺ…사, 동사, μ „μΉ˜μ‚¬, ν˜•μš©μ‚¬κ°€ 두루 쓰인닀. (ex) `Inject`, `ImplementedBy`) + +### ☁️ λ©”μ„œλ“œ +μ–΄λ–€ λ™μž‘μ„ μˆ˜ν–‰ν•˜λŠ” λ©”μ„œλ“œ 이름은 **λ™μ‚¬λ‚˜ 동사ꡬ**둜 μ§“λŠ”λ‹€. 단, λ™μ‚¬λŠ” **ν˜„μž¬ν˜•**이여야 ν•œλ‹€. (ex) `drawImage` ) + ++ `is`, `has` : `boolean` 값을 λ°˜ν™˜ν•˜λŠ” λ©”μ„œλ“œ (ex) `isDigit`, `hasSiblings`) + ++ `λͺ…사`, `get` : ν•΄λ‹Ή μΈμŠ€ν„΄μŠ€μ˜ 속성을 λ°˜ν™˜ν•˜λ©΄μ„œ λ°˜ν™˜ νƒ€μž…μ΄ `boolean` 이 μ•„λ‹Œκ²½μš° (ex) `size`, `getTime` ) + ```java + if (car.speed() > 2 * SPEED_LIMIT) + generateAudibleAlert("κ²½μ°° μ‘°μ‹¬ν•˜μ„Έμš”!"); + ``` + ++ `toType` : 객체의 νƒ€μž…μ„ λ°”κΏ”μ„œ λ‹€λ₯Έ νƒ€μž…μ˜ λ‹€λ₯Έ 객체λ₯Ό λ°˜ν™˜ν•˜λŠ” μΈμŠ€ν„΄μŠ€ λ©”μ„œλ“œ (ex) `toString`, `toArray` ) + ++ `asType` : 객체의 λ‚΄μš©μ„ λ‹€λ₯Έ 뷰둜 λ³΄μ—¬μ£ΌλŠ” λ©”μ„œλ“œ (ex) `asList` ) + ++ `typeValue` : 객체의 값을 κΈ°λ³Έ νƒ€μž… κ°’μœΌλ‘œ λ°˜ν™˜ν•˜λŠ” λ©”μ„œλ“œ (ex) `intValue` ) + +>πŸ”– **정적 νŒ©ν„°λ¦¬ 이름** +from, of, valueOf, instance, getInstance, newInstance, getType, newType을 ν”νžˆ μ‚¬μš© + + +### ☁️ ν•„λ“œ 이름 +ν•„λ“œ 이름에 κ΄€ν•œ 문법 κ·œμΉ™μ€ 클래슀, μΈν„°νŽ˜μ΄μŠ€, λ©”μ„œλ“œ 이름에 λΉ„ν•΄ 덜 λͺ…ν™•ν•˜κ³  덜 μ€‘μš”ν•˜λ‹€. API 섀계λ₯Ό 잘 ν–ˆλ‹€λ©΄ ν•„λ“œκ°€ 직접 λ…ΈμΆœλ  일이 거의 μ—†κΈ° λ•Œλ¬Έμ΄λ‹€. + ++ `boolean` νƒ€μž… : boolean μ ‘κ·Όμž λ©”μ„œλ“œμ—μ„œ μ•ž 단어λ₯Ό λΊ€ ν˜•νƒœ ++ μ΄μ™Έμ˜ νƒ€μž… : λͺ…사 / λͺ…사ꡬ μ‚¬μš© diff --git "a/Ch10/item73/\354\266\224\354\203\201\355\231\224_\354\210\230\354\244\200\354\227\220_\353\247\236\353\212\224_\354\230\210\354\231\270\353\245\274_\353\215\230\354\247\200\353\235\274.md" "b/Ch10/item73/\354\266\224\354\203\201\355\231\224_\354\210\230\354\244\200\354\227\220_\353\247\236\353\212\224_\354\230\210\354\231\270\353\245\274_\353\215\230\354\247\200\353\235\274.md" new file mode 100644 index 0000000..a5542b0 --- /dev/null +++ "b/Ch10/item73/\354\266\224\354\203\201\355\231\224_\354\210\230\354\244\200\354\227\220_\353\247\236\353\212\224_\354\230\210\354\231\270\353\245\274_\353\215\230\354\247\200\353\235\274.md" @@ -0,0 +1,72 @@ +λ©”μ„œλ“œκ°€ **μ €μˆ˜μ€€ μ˜ˆμ™Έλ₯Ό μ²˜λ¦¬ν•˜μ§€ μ•Šκ³  λ°”κΉ₯으둜 μ „νŒŒ**( `throws` )해버릴 λ•Œ, μˆ˜ν–‰ν•˜λ €λŠ” 일과 κ΄€λ ¨ μ—†μ–΄ λ³΄μ΄λŠ” μ˜ˆμ™Έκ°€ νŠ€μ–΄λ‚˜μ˜¨λ‹€. μ΄λŠ” λ‚΄λΆ€ κ΅¬ν˜„ 방식을 λ“œλŸ¬λ‚΄μ–΄ μœ— 레벨의 APIλ₯Ό μ˜€μ—Όμ‹œν‚¬ 수 μžˆμœΌλ―€λ‘œ μœ„ν—˜ν•˜λ‹€. + +#### Spring +λŒ€ν‘œμ μΈ μ˜ˆμ‹œλ‘œ, μŠ€ν”„λ§μ—μ„œλ„ 데이터 κ³„μΈ΅μ—μ„œ νŠΉμ • DB에 μ’…μ†λ˜λŠ” `SQLException` κ³Ό 같은 μ €μˆ˜μ€€ μ˜ˆμ™Έλ₯Ό, μ˜ˆμ™Έ λ³€ν™˜κΈ° ( `PersistenceExceptionTranslator`) λ₯Ό 톡해 κ³ μˆ˜μ€€ `DataAccessException` 으둜 λ³€ν™˜μ‹œν‚¨λ‹€. + +### ☁️ μ˜ˆμ™Έ λ²ˆμ—­(Exception Translation) +이 문제λ₯Ό ν”Όν•˜λ €λ©΄, **μƒμœ„ κ³„μΈ΅μ—μ„œλŠ” μ €μˆ˜μ€€ μ˜ˆμ™Έλ₯Ό μž‘μ•„ μžμ‹ μ˜ 좔상화 μˆ˜μ€€μ— λ§žλŠ” μ˜ˆμ™Έλ‘œ λ°”κΎΈμ–΄ λ˜μ Έμ•Ό** ν•œλ‹€. 그리고 이λ₯Ό **μ˜ˆμ™Έ λ²ˆμ—­**이라 ν•œλ‹€. + +```java +try { + ... +} catch (LowerLevelException e) { + throw new HigherLevelException(...); +} +``` + +μ˜ˆμ™Έ λ²ˆμ—­μ„ μ‚¬μš©ν•œ 예둜 `AbstractSequentialList` λ₯Ό λ“€μ–΄λ³΄μž. + +#### AbstractSequentialList + +```java +/** + 이 리슀트 μ•ˆμ˜ μ§€μ •ν•œ μœ„μΉ˜μ˜ μ›μ†Œλ₯Ό λ°˜ν™˜ν•œλ‹€. + @throws IndexOutOfBoundsException indexκ°€ λ²”μœ„ 밖이라면, + 즉 {@code index < 0 || index >= size()}이면 λ°œμƒν•œλ‹€. +**/ +public E get(int idex) { + ListIterator i = listIterator(index); + try { + return i.next(); + } catch (NoSuchElementException e) { + throw new IndexOutOfBoundsException("인덱슀: " + index); + } +} +``` + +### ☁️ μ˜ˆμ™Έ 연쇄(Exception Chaining) + +μ˜ˆμ™Έ μ—°μ‡„λž€, 문제의 κ·Όλ³Έ 원인인 μ €μˆ˜μ€€ μ˜ˆμ™Έλ₯Ό κ³ μˆ˜μ€€ μ˜ˆμ™Έμ— μ‹€μ–΄ λ³΄λ‚΄λŠ” 방식이닀. λ”°λΌμ„œ μ˜ˆμ™Έλ₯Ό λ²ˆμ—­ν•  λ•Œ, μ €μˆ˜μ€€ μ˜ˆμ™Έκ°€ 디버깅에 도움이 λœλ‹€λ©΄ μ˜ˆμ™Έ 연쇄λ₯Ό μ‚¬μš©ν•˜λ„λ‘ ν•˜μž. + +```java +try { + ... +} catch (LowerLevelException cause) { + // μ €μˆ˜μ€€ μ˜ˆμ™Έλ₯Ό κ³ μˆ˜μ€€ μ˜ˆμ™Έμ— μ‹€μ–΄ 보낸닀. + throw new HigherLevelException(cause); +} + +``` + +λŒ€λΆ€λΆ„μ˜ ν‘œμ€€ μ˜ˆμ™ΈλŠ” μ•„λž˜μ™€ 같이 μ˜ˆμ™Έ μ—°μ‡„μš© μƒμ„±μžλ₯Ό κ°–μΆ”κ³  μžˆλ‹€. +```java +class HigherLevelException extends Exception { + HigherLevelException(Throwable cause) { + super(cause); + } +} +``` +문제의 원인을 `getCause` λ©”μ„œλ“œλ‘œ ν”„λ‘œκ·Έλž¨μ—μ„œ μ ‘κ·Όν•  수 있게 ν•΄μ£Όμ–΄, 원인과 κ³ μˆ˜μ€€ μ˜ˆμ™Έμ˜ μŠ€νƒ 좔적 정보λ₯Ό 잘 톡합해쀀닀. + +### ☁️ 주의 사항 +결둠적으둜 μ˜ˆμ™Έλ₯Ό μ „νŒŒ( `throws` )ν•˜λŠ” 것보닀 μ˜ˆμ™Έ λ²ˆμ—­μ΄ 더 λ‚˜μ€ λ°©λ²•μ΄μ§€λ§Œ, λ‚¨μš©ν•΄μ„œλŠ” μ•ˆλœλ‹€. μš°μ„ μˆœμœ„λŠ” λ‹€μŒκ³Ό κ°™λ‹€. + +1. κ°€λŠ₯ν•˜λ‹€λ©΄ μ €μˆ˜μ€€ λ©”μ„œλ“œκ°€ λ°˜λ“œμ‹œ 성곡해 μ˜ˆμ™Έλ₯Ό λ°œμƒμ‹œν‚€μ§€ μ•Šλ„λ‘ ν•œλ‹€. +2. μƒμœ„ 계측 λ©”μ„œλ“œμ˜ λ§€κ°œλ³€μˆ˜ 값을 μ•„λž˜λ‘œ λ„˜κΈ°κΈ° 전에 미리 κ²€μ‚¬ν•œλ‹€. +3. μ˜ˆμ™Έλ₯Ό 예방 및 처리 λΆˆκ°€λŠ₯ν• λ•Œ μ˜ˆμ™Έ λ²ˆμ—­μ„ μ‚¬μš©ν•œλ‹€. + +λ§Œμ•½ μ•„λž˜ κ³„μΈ΅μ—μ„œμ˜ μ˜ˆμ™Έκ°€ λΆˆκ°€ν”Όν•˜λ‹€λ©΄, μƒμœ„ κ³„μΈ΅μ—μ„œ μ˜ˆμ™Έλ₯Ό 쑰용이 μ²˜λ¦¬ν•˜μ—¬ API ν˜ΈμΆœμžμ—κ²ŒκΉŒμ§€ μ „νŒŒν•˜μ§€ μ•ŠλŠ” 방법도 μ‘΄μž¬ν•œλ‹€. 이 경우, λ°œμƒν•œ μ˜ˆμ™ΈλŠ” `java.util.logging` 같은 λ‘œκΉ… κΈ°λŠ₯을 ν™œμš©ν•˜μ—¬ κΈ°λ‘ν•΄λ‘μž. + + +> πŸ“š **핡심 정리**
+μ•„λž˜ κ³„μΈ΅μ˜ μ˜ˆμ™Έλ₯Ό μ˜ˆλ°©ν•˜κ±°λ‚˜ 슀슀둜 μ²˜λ¦¬ν•  수 μ—†κ³ , μƒμœ„ 계측에 κ·ΈλŒ€λ‘œ λ…ΈμΆœν•˜κΈ° κ³€λž€ν•˜λ‹€λ©΄ μ˜ˆμ™Έ λ²ˆμ—­μ„ μ‚¬μš©ν•˜μž. μ΄λ•Œ μ˜ˆμ™Έ 연쇄λ₯Ό μ΄μš©ν•˜λ©΄ μƒμœ„ κ³„μΈ΅μ—λŠ” λ§₯락에 μ–΄μšΈλ¦¬λŠ” κ³ μˆ˜μ€€ μ˜ˆμ™Έλ₯Ό λ˜μ§€λ©΄μ„œ, κ·Όλ³Έ 원인도 ν•¨κ»˜ μ•Œλ €μ£Όμ–΄ 였λ₯˜λ₯Ό λΆ„μ„ν•˜κΈ°μ— μ’‹λ‹€.