๐Ÿ‘จ๐Ÿปโ€๐Ÿ’ป ์ดํŽ™ํ‹ฐ๋ธŒ ์ž๋ฐ” - ๋ฉ”์„œ๋“œ

Peterยท2022๋…„ 3์›” 22์ผ
0
post-thumbnail

8์žฅ - ๋ฉ”์„œ๋“œ


๐Ÿ’ก ๋งค๊ฐœ๋ณ€์ˆ˜๊ฐ€ ์œ ํšจํ•œ์ง€ ๊ฒ€์‚ฌํ•˜๋ผ

โ€œ๋งค๊ฐœ๋ณ€์ˆ˜์˜ ์ œ์•ฝ๋“ค์„ ๋ฌธ์„œํ™”ํ•˜๊ณ  ๋ฉ”์„œ๋“œ ์ฝ”๋“œ ์‹œ์ž‘ ๋ถ€๋ถ„์—์„œ ๋ช…์‹œ์ ์œผ๋กœ ๊ฒ€์‚ฌํ•˜์žโ€

1. ๋งค๊ฐœ๋ณ€์ˆ˜ ๊ฒ€์‚ฌ

  • ๋งค๊ฐœ๋ณ€์ˆ˜ ๊ฒ€์‚ฌ๋ฅผ ์ˆ˜ํ–‰ํ•˜์ง€ ์•Š์•˜์„ ๋•Œ ๋ฌธ์ œ์ 
    1. ๋ฉ”์„œ๋“œ๊ฐ€ ์ˆ˜ํ–‰๋˜๋Š” ์ค‘๊ฐ„์— ๋ชจํ˜ธํ•œ ์˜ˆ์™ธ๋ฅผ ๋˜์ง€๋ฉฐ ์‹คํŒจํ•  ์ˆ˜ ์žˆ์Œ.
    2. ๋ฉ”์„œ๋“œ๊ฐ€ ์ž˜ ์ˆ˜ํ–‰๋˜์ง€๋งŒ ์ž˜๋ชป๋œ ๊ฒฐ๊ณผ๋ฅผ ๋ฐ˜ํ™˜ํ•  ์ˆ˜ ์žˆ์Œ
    3. ๋ฉ”์„œ๋“œ๋Š” ๋ฌธ์ œ์—†์ด ์ˆ˜ํ–‰๋์ง€๋งŒ, ์–ด๋–ค ๊ฐ์ฒด๋ฅผ ์ด์ƒํ•œ ์ƒํƒœ๋กœ ๋งŒ๋“ค์–ด์„œ ๋ฏธ๋ž˜์˜ ์•Œ ์ˆ˜ ์—†๋Š” ์‹œ์ ์— ์ด ๋ฉ”์„œ๋“œ์™€๋Š” ๊ด€๋ จ ์—†๋Š” ์˜ค๋ฅ˜๋ฅผ ๋‚ผ ์ˆ˜ ์žˆ์Œ.

โ†’ ๋งค๊ฐœ๋ณ€์ˆ˜ ๊ฒ€์‚ฌ์— ์‹คํŒจํ•˜๋ฉด ์‹คํŒจ ์›์ž์„ฑ(failure atomicity)์„ ์–ด๊ธฐ๋Š” ๊ฒฐ๊ณผ๋ฅผ ๋‚ณ์„ ์ˆ˜ ์žˆ์Œ.

  • ๋งค๊ฐœ๋ณ€์ˆ˜ ๊ฒ€์‚ฌ๋Š” ๋ฉ”์„œ๋“œ ๋ชธ์ฒด๊ฐ€ ์‹คํ–‰๋˜๊ธฐ ์ „์— ์ง„ํ–‰ํ•ด์•ผ ํ•จ.
  • ๋งค๊ฐœ๋ณ€์ˆ˜์˜ ์ œ์•ฝ์„ ๋ฌธ์„œํ™”ํ•œ๋‹ค๋ฉด ๊ทธ ์ œ์•ฝ์„ ์–ด๊ฒผ์„ ๋•Œ ๋ฐœ์ƒํ•˜๋Š” ์˜ˆ์™ธ๋„ ํ•จ๊ป˜ ๊ธฐ์ˆ ํ•ด์•ผ ํ•จ.

2. ๋‹จ์–ธ๋ฌธ(assert)

  • ๊ณต๊ฐœ๋˜์ง€ ์•Š์€ ๋ฉ”์„œ๋“œ๋ผ๋ฉด ํŒจํ‚ค์ง€ ์ œ์ž‘์ž๊ฐ€ ๋ฉ”์„œ๋“œ๊ฐ€ ํ˜ธ์ถœ๋˜๋Š” ์ƒํ™ฉ์„ ํ†ต์ œํ•  ์ˆ˜ ์žˆ์Œ.
    • ๋”ฐ๋ผ์„œ ์˜ค์ง ์œ ํšจํ•œ ๊ฐ’๋งŒ์ด ๋ฉ”์„œ๋“œ์— ๋„˜๊ฒจ์ง€๋ฆฌ๋ผ๋Š” ๊ฒƒ์„ ๋ณด์ฆํ•  ์ˆ˜ ์žˆ๊ณ , ๊ทธ๋ ‡๊ฒŒ ํ•ด์•ผ ํ•จ.

โ†’ public์ด ์•„๋‹Œ ๋ฉ”์„œ๋“œ๋ผ๋ฉด ๋‹จ์–ธ๋ฌธ(assert)์„ ์‚ฌ์šฉํ•ด ๋งค๊ฐœ๋ณ€์ˆ˜ ์œ ํšจ์„ฑ์„ ๊ฒ€์ฆํ•  ์ˆ˜ ์žˆ์Œ.

  • ๋‹จ์–ธ๋ฌธ ์„ค๋ช…
    1. ์‹คํŒจํ•˜๋ฉด AssertionError ๋ฅผ ๋˜์ง„๋‹ค.
    2. ๋Ÿฐํƒ€์ž„์— ์•„๋ฌด๋Ÿฐ ํšจ๊ณผ๋„, ์•„๋ฌด๋Ÿฐ ์„ฑ๋Šฅ ์ €ํ•˜๋„ ์—†๋‹ค.


๐Ÿ’ก ์ ์‹œ์— ๋ฐฉ์–ด์  ๋ณต์‚ฌ๋ณธ์„ ๋งŒ๋“ค๋ผ

โ€œํด๋ž˜์Šค๊ฐ€ ํด๋ผ์ด์–ธํŠธ๋กœ๋ถ€ํ„ฐ ๋ฐ›๋Š” ํ˜น์€ ํด๋ผ์ด์–ธํŠธ๋กœ ๋ฐ˜ํ™˜ํ•˜๋Š” ๊ตฌ์„ฑ์š”์†Œ๊ฐ€ ๊ฐ€๋ณ€์ด๋ผ๋ฉด
๊ทธ ์š”์†Œ๋Š” ๋ฐ˜๋“œ์‹œ
๋ฐฉ์–ด์ ์œผ๋กœ ๋ณต์‚ฌํ•ด์•ผ ํ•œ๋‹คโ€

1. ๋ฐฉ์–ด์  ๋ณต์‚ฌ ์˜ˆ์‹œ

// ๊ธฐ๊ฐ„์„ ํ‘œํ˜„ํ•˜๋Š” ํด๋ž˜์Šค - ๋ถˆ๋ณ€์‹์„ ์ง€ํ‚ค์ง€ ๋ชปํ–ˆ๋‹ค.
public final class Period {
    private final Date start;
    private final Date end;

    /**
     * @param  start ์‹œ์ž‘ ์‹œ๊ฐ
     * @param  end ์ข…๋ฃŒ ์‹œ๊ฐ. ์‹œ์ž‘ ์‹œ๊ฐ๋ณด๋‹ค ๋’ค์—ฌ์•ผ ํ•œ๋‹ค.
     * @throws IllegalArgumentException ์‹œ์ž‘ ์‹œ๊ฐ์ด ์ข…๋ฃŒ ์‹œ๊ฐ๋ณด๋‹ค ๋Šฆ์„ ๋•Œ ๋ฐœ์ƒํ•œ๋‹ค.
     * @throws NullPointerException start๋‚˜ end๊ฐ€ null์ด๋ฉด ๋ฐœ์ƒํ•œ๋‹ค.
     */
    public Period(Date start, Date end) {
        if (start.compareTo(end) > 0)
            throw new IllegalArgumentException(
                    start + "๊ฐ€ " + end + "๋ณด๋‹ค ๋Šฆ๋‹ค.");
        this.start = start;
        this.end   = end;
    }

    public Date start() {
        return start;
    }
    public Date end() {
        return end;
    }

    public String toString() {
        return start + " - " + end;
    }
    // ๋‚˜๋จธ์ง€ ์ฝ”๋“œ ์ƒ๋žต
}
  • ์œ„์˜ ์ฝ”๋“œ์—์„œ Date๊ฐ€ ๊ฐ€๋ณ€์ด๋ผ๋Š” ์‚ฌ์‹ค์„ ์ด์šฉํ•˜๋ฉด ์‰ฝ๊ฒŒ ๋ถˆ๋ณ€์‹์„ ๊นจ๋œจ๋ฆด ์ˆ˜ ์žˆ์Œ
// Period ์ธ์Šคํ„ด์Šค์˜ ๋ถˆ๋ณ€์‹์„ ๊นจ๋œจ๋ฆฌ๋Š” ์˜ˆ์‹œ
Date start = new Date();
Date end = new Date();
Period p = new Period(start, end);
end.setYear(78); // p์˜ ๋‚ด๋ถ€๋ฅผ ์‰ฝ๊ฒŒ ์ˆ˜์ •.
  • [์ฐธ๊ณ ] Date ๊ฐ์ฒด๋Š” ๋‚ก์€ API์ด๋‹ˆ ์ƒˆ๋กœ์šด ์ฝ”๋“œ๋ฅผ ์ž‘์„ฑํ•  ๋•Œ๋Š” ๋” ์ด์ƒ ์‚ฌ์šฉํ•˜๋ฉด ์•ˆ ๋จ
    • LocalDateTime์ด๋‚˜ ZonedDateTime ํ˜น์€ Instant๋ฅผ ์‚ฌ์šฉํ•˜์ž
  • ๊ทธ๋ ‡๋‹ค๋ฉด Period๋ฅผ ๋ถˆ๋ณ€์œผ๋กœ ๋งŒ๋“œ๋Š” ๋ฐฉ๋ฒ•์€ ๋ฌด์—‡์ผ๊นŒ?

โ†’ ์ƒ์„ฑ์ž์—์„œ ๋ฐ›์€ ๊ฐ€๋ณ€ ๋งค๊ฐœ๋ณ€์ˆ˜๋ฅผ ๊ฐ๊ฐ ๋ฐฉ์–ด์ ์œผ๋กœ ๋ณต์‚ฌ(defensive copy)ํ•˜์ž

// ์ˆ˜์ •ํ•œ ์ƒ์„ฑ์ž - ๋งค๊ฐœ๋ณ€์ˆ˜์˜ ๋ฐฉ์–ด์  ๋ณต์‚ฌ๋ณธ์„ ๋งŒ๋“ ๋‹ค.
public Period(Date start, Date end) {
    this.start = new Date(start.getTime());
    this.end   = new Date(end.getTime());

		// ๋งค๊ฐœ๋ณ€์ˆ˜ ์œ ํšจ์„ฑ ๊ฒ€์‚ฌ
    if (this.start.compareTo(this.end) > 0)
        throw new IllegalArgumentException(
                this.start + "๊ฐ€ " + this.end + "๋ณด๋‹ค ๋Šฆ๋‹ค.");
}
  • ๋งค๊ฐœ๋ณ€์ˆ˜์˜ ์œ ํšจ์„ฑ์„ ๊ฒ€์‚ฌํ•˜๊ธฐ ์ „์— ๋ฐฉ์–ด์  ๋ณต์‚ฌ๋ณธ์„ ๋งŒ๋“ค๊ณ , ์ด ๋ณต์‚ฌ๋ณธ์œผ๋กœ ์œ ํšจ์„ฑ์„ ๊ฒ€์‚ฌํ•œ ์ ์— ์ฃผ๋ชฉํ•˜์ž.
    • ๋ฐ˜๋“œ์‹œ ์ด๋ ‡๊ฒŒ ์ž‘์„ฑํ•ด์•ผ ํ•จ.
    • Why? ๋ฉ€ํ‹ฐ์Šค๋ ˆ๋”ฉ ํ™˜๊ฒฝ์ด๋ผ๋ฉด ์›๋ณธ ๊ฐ์ฒด์˜ ์œ ํšจ์„ฑ์„ ๊ฒ€์‚ฌํ•œ ํ›„ ๋ณต์‚ฌ๋ณธ์„ ๋งŒ๋“œ๋Š” ๊ทธ ์ฐฐ๋‚˜์˜ ์ทจ์•ฝํ•œ ์ˆœ๊ฐ„์— ๋‹ค๋ฅธ ์Šค๋ ˆ๋“œ๊ฐ€ ์›๋ณธ ๊ฐ์ฒด๋ฅผ ์ˆ˜์ •ํ•  ์œ„ํ—˜์ด ์žˆ๊ธฐ ๋•Œ๋ฌธ.
      • ์ด๋Ÿฌํ•œ ๊ณต๊ฒฉ์„ ๊ฒ€์‚ฌ์‹œ์ /์‚ฌ์šฉ์‹œ์ (time-of-check/time-of-use), TOCTOU ๊ณต๊ฒฉ์ด๋ผ๊ณ  ํ•จ.
  • ์•„์ง Period ํด๋ž˜์Šค๋Š” ์ทจ์•ฝํ•˜๋‹ค. ์ ‘๊ทผ์ž๊ฐ€ ๋‚ด๋ถ€์˜ ๊ฐ€๋ณ€ ์ •๋ณด๋ฅผ ์ง์ ‘ ๋“œ๋Ÿฌ๋‚ด๊ณ  ์žˆ์Œ. ์•„๋ž˜์™€ ๊ฐ™์€ ๊ณต๊ฒฉ์ด ๊ฐ€๋Šฅํ•จ
Date start = new Date();
Date end = new Date();
Period p = new Period(start, end);
p.end().setYear(78); // p์˜ ๋‚ด๋ถ€๋ฅผ ์‰ฝ๊ฒŒ ๋ณ€๊ฒฝ
  • ์ด ๊ณต๊ฒฉ์„ ๋ง‰์œผ๋ ค๋ฉด ์•„๋ž˜์™€ ๊ฐ™์ด ๋‹จ์ˆœํžˆ ์ ‘๊ทผ์ž๊ฐ€ ๊ฐ€๋ณ€ ํ•„๋“œ์˜ ๋ฐฉ์–ด์  ๋ณต์‚ฌ๋ณธ์„ ๋ฐ˜ํ™˜ํ•˜๋ฉด ๋จ.
// ์ˆ˜์ •ํ•œ ์ ‘๊ทผ์ž - ํ•„๋“œ์˜ ๋ฐฉ์–ด์  ๋ณต์‚ฌ๋ณธ์„ ๋ฐ˜ํ™˜ํ•œ๋‹ค.
public Date start() {
    return new Date(start.getTime());
}

public Date end() {
    return new Date(end.getTime()) ;
}

โ†’ ์ด์ œ Period ์ž์‹  ๋ง๊ณ ๋Š” ๊ฐ€๋ณ€ ํ•„๋“œ์— ์ ‘๊ทผํ•  ๋ฐฉ๋ฒ•์ด ์—†๋‹ค. (๋ชจ๋“  ํ•„๋“œ๊ฐ€ ๊ฐ์ฒด ์•ˆ์— ์™„๋ฒฝํžˆ ์บก์Šํ™”)

  • ๊ตํ›ˆ : โ€œ๋˜๋„๋ก ๋ถˆ๋ณ€ ๊ฐ์ฒด๋“ค์„ ์กฐํ•ฉํ•ด ๊ฐ์ฒด๋ฅผ ๊ตฌ์„ฑํ•ด์•ผ ๋ฐฉ์–ด์  ๋ณต์‚ฌ๋ฅผ ํ•  ์ผ์ด ์ค„์–ด๋“ ๋‹คโ€

2. ๋ฐฉ์–ด์  ๋ณต์‚ฌ์˜ ์ˆ˜ํ–‰

  • ๊ฐ€๋ณ€ ๊ฐ์ฒด๋ผ๋ฉด ๊ทธ ๊ฐ์ฒด๊ฐ€ ํด๋ž˜์Šค์— ๋„˜๊ฒจ์ง„ ๋’ค ์ž„์˜๋กœ ๋ณ€๊ฒฝ๋˜์–ด๋„ ๊ทธ ํด๋ž˜์Šค๊ฐ€ ๋ฌธ์ œ์—†์ด ๋™์ž‘ํ• ์ง€๋ฅผ ๋”ฐ์ ธ๋ณด์ž

โ†’ ํ™•์‹ ํ•  ์ˆ˜ ์—†๋‹ค๋ฉด ๋ฐฉ์–ด์  ๋ณต์‚ฌ๋ณธ์„ ์ €์žฅํ•˜์ž

  • ๋ฐฉ์–ด์  ๋ณต์‚ฌ๋ฅผ ์ˆ˜ํ–‰ํ•˜์ง€ ์•Š์•„๋„ ๋˜๋Š” ๊ฒฝ์šฐ
    1. (๊ฐ™์€ ํŒจํ‚ค์ง€์— ์†ํ•˜๋Š” ๋“ฑ์˜ ์ด์œ ๋กœ) ํด๋ผ์ด์–ธํŠธ๊ฐ€ ์ปดํฌ๋„ŒํŠธ ๋‚ด๋ถ€๋ฅผ ์ˆ˜์ •ํ•˜์ง€ ์•Š์œผ๋ฆฌ๋ผ ํ™•์‹ ํ•  ์ˆ˜ ์žˆ์„ ๋•Œ
    2. ๋ฐฉ์–ด์  ๋ณต์‚ฌ ๋น„์šฉ์ด ๋„ˆ๋ฌด ํด ๋•Œ.

โ†’ ์ด๋Ÿฐ ๊ฒฝ์šฐ์— ๋ฐฉ์–ด์  ๋ณต์‚ฌ๋ฅผ ์ˆ˜ํ–‰ํ•˜๋Š” ๋Œ€์‹  ํ•ด๋‹น ๊ตฌ์„ฑ์š”์†Œ๋ฅผ ์ˆ˜์ •ํ–ˆ์„ ๋•Œ์˜ ์ฑ…์ž„์ด ํด๋ผ์ด์–ธํŠธ์— ์žˆ์Œ์„ ๋ฌธ์„œ์— ๋ช…์‹œํ•˜์ž.



๐Ÿ’ก ๋ฉ”์„œ๋“œ ์‹œ๊ทธ๋‹ˆ์ฒ˜๋ฅผ ์‹ ์ค‘ํžˆ ์„ค๊ณ„ํ•˜๋ผ

โ€œAPI ์„ค๊ณ„ ์š”๋ นโ€

1. ๋ฉ”์„œ๋“œ ์ด๋ฆ„์„ ์‹ ์ค‘ํžˆ ์ง“์ž

  • ํ•ญ์ƒ ํ‘œ์ค€ ๋ช…๋ช… ๊ทœ์น™์„ ๋”ฐ๋ผ์•ผ ํ•จ.
  • ๊ฐ™์€ ํŒจํ‚ค์ง€์— ์†ํ•œ ๋‹ค๋ฅธ ์ด๋ฆ„๋“ค๊ณผ ์ผ๊ด€๋˜๊ฒŒ ์ง“๋Š” ๊ฒŒ ์ตœ์šฐ์„  ๋ชฉํ‘œ
  • ๊ฐœ๋ฐœ์ž ์ปค๋ฎค๋‹ˆํ‹ฐ์—์„œ ๋„๋ฆฌ ๋ฐ›์•„๋“ค์—ฌ์ง€๋Š” ์ด๋ฆ„์„ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์ด ๊ทธ ๋‹ค์Œ ๋ชฉํ‘œ
  • ์• ๋งคํ•˜๋ฉด ์ž๋ฐ” ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ API ๊ฐ€์ด๋“œ๋ฅผ ์ฐธ์กฐํ•˜์ž.

2. ํŽธ์˜ ๋ฉ”์„œ๋“œ๋ฅผ ๋„ˆ๋ฌด ๋งŽ์ด ๋งŒ๋“ค์ง€ ๋ง์ž

  • ๋ฉ”์„œ๋“œ๊ฐ€ ๋„ˆ๋ฌด ๋งŽ์€ ํด๋ž˜์Šค(ํ˜น์€ ์ธํ„ฐํŽ˜์ด์Šค)๋Š” ์ตํžˆ๊ณ , ์‚ฌ์šฉํ•˜๊ณ , ๋ฌธ์„œํ™”ํ•˜๊ณ , ํ…Œ์ŠคํŠธํ•˜๊ณ , ์œ ์ง€๋ณด์ˆ˜ํ•˜๊ธฐ ์–ด๋ ค์›€.

โ†’ ํ™•์‹ ์ด ์„œ์ง€ ์•Š์œผ๋ฉด ๋งŒ๋“ค์ง€ ๋ง์ž


3. ๋งค๊ฐœ๋ณ€์ˆ˜ ๋ชฉ๋ก์€ ์งง๊ฒŒ ์œ ์ง€ํ•˜์ž

  • 4๊ฐœ ์ดํ•˜๊ฐ€ ์ข‹์Œ
  • ๊ฐ™์€ ํƒ€์ž…์˜ ๋งค๊ฐœ๋ณ€์ˆ˜๊ฐ€ ์—ฐ๋‹ฌ์•„ ๋‚˜์˜ค๋Š” ๊ฒƒ์€ ํ•ด๋กญ๋‹ค..
    • ์‹ค์ˆ˜๋กœ ์ˆœ์„œ๋ฅผ ๋ฐ”๊ฟ” ์ž…๋ ฅํ•ด๋„ ๊ทธ๋Œ€๋กœ ์ปดํŒŒ์ผ๋˜๊ณ  ์‹คํ–‰ ๋จ. ๋‹จ์ง€ ์˜๋„์™€ ๋‹ค๋ฅด๊ฒŒ ๋™์ž‘ํ•  ๋ฟ..
  • ๊ณผํ•˜๊ฒŒ ๊ธด ๋งค๊ฐœ๋ณ€์ˆ˜ ๋ชฉ๋ก์„ ์งง๊ฒŒ ์ค„์—ฌ์ฃผ๋Š” ๊ธฐ์ˆ  3๊ฐ€์ง€
    1. ์—ฌ๋Ÿฌ ๋ฉ”์„œ๋“œ๋กœ ์ชผ๊ฐ ๋‹ค.
    2. ๋งค๊ฐœ๋ณ€์ˆ˜ ์—ฌ๋Ÿฌ ๊ฐœ๋ฅผ ๋ฌถ์–ด์ฃผ๋Š” ๋„์šฐ๋ฏธ ํด๋ž˜์Šค๋ฅผ ๋งŒ๋“ ๋‹ค.
      • ์ผ๋ฐ˜์ ์œผ๋กœ ์ด๋Ÿฐ ๋„์šฐ๋ฏธ ํด๋ž˜์Šค๋Š” ์ •์  ๋ฉค๋ฒ„ ํด๋ž˜์Šค๋กœ ๋‘ 
    3. ๋นŒ๋” ํŒจํ„ด์„ ๋ฉ”์„œ๋“œ ํ˜ธ์ถœ์— ์‘์šฉํ•œ๋‹ค.
      • ๋งค๊ฐœ๋ณ€์ˆ˜๋ฅผ ํ•˜๋‚˜๋กœ ์ถ”์ƒํ™”ํ•œ ๊ฐ์ฒด๋ฅผ ์ •์˜ํ•˜๊ณ , ํด๋ผ์ด์–ธํŠธ์—์„œ ์ด ๊ฐ์ฒด์˜ ์„ธํ„ฐ(setter) ๋ฉ”์„œ๋“œ๋ฅผ ํ˜ธ์ถœํ•ด ํ•„์š”ํ•œ ๊ฐ’์„ ์„ค์ •ํ•˜๊ฒŒ ํ•˜๋Š” ๋ฐฉ์‹.
      • ์œ ํšจ์„ฑ ๊ฒ€์ฆ ๋ฐ ์„ค์ •์ด ์™„๋ฃŒ๋œ ๊ฐ์ฒด๋ฅผ ๋ฉ”์„œ๋“œ์— ๋„˜๊ธฐ๋ฉด ๋จ.
      • ๋งค๊ฐœ๋ณ€์ˆ˜๊ฐ€ ๋งŽ๊ณ  ๊ทธ ์ค‘ ์ผ๋ถ€๋Š” ์ƒ๋žตํ•ด๋„ ๊ดœ์ฐฎ์„ ๋•Œ ๋„์›€์ด ๋˜๋Š” ๋ฐฉ์‹

4. ๋งค๊ฐœ๋ณ€์ˆ˜์˜ ํƒ€์ž…์œผ๋กœ๋Š” ํด๋ž˜์Šค๋ณด๋‹ค๋Š” ์ธํ„ฐํŽ˜์ด์Šค๊ฐ€ ๋” ๋‚ซ๋‹ค

  • ์ธํ„ฐํŽ˜์ด์Šค ๋Œ€์‹  ํด๋ž˜์Šค๋ฅผ ์‚ฌ์šฉํ•˜๋ฉด ํด๋ผ์ด์–ธํŠธ์—๊ฒŒ ํŠน์ • ๊ตฌํ˜„์ฒด๋งŒ ์‚ฌ์šฉํ•˜๋„๋ก ์ œํ•œํ•˜๋Š” ๊ผด.
    • ํ˜น์‹œ๋ผ๋„ ์ž…๋ ฅ ๋ฐ์ดํ„ฐ๊ฐ€ ๋‹ค๋ฅธ ํ˜•ํƒœ๋กœ ์กด์žฌํ•œ๋‹ค๋ฉด ๋ช…์‹œํ•œ ํŠน์ • ๊ตฌํ˜„์ฒด๋กœ ์˜ฎ๊ฒจ ๋‹ด๋Š๋ผ ๋น„์‹ผ ๋ณต์‚ฌ ๋น„์šฉ์„ ์น˜๋Ÿฌ์•ผ ํ•จ.

5. ๋งค๊ฐœ๋ณ€์ˆ˜๋กœ boolean๋ณด๋‹ค๋Š” ์›์†Œ 2๊ฐœ์งœ๋ฆฌ ์—ด๊ฑฐ ํƒ€์ž…์ด ๋‚ซ๋‹ค

  • ๋ฉ”์„œ๋“œ ์ด๋ฆ„์ƒ boolean์„ ๋ฐ›์•„์•ผ ์˜๋ฏธ๊ฐ€ ๋” ๋ช…ํ™•ํ•  ๊ฒฝ์šฐ๋Š” ์˜ˆ์™ธ์ž„.
  • Thermometer.newInstance(true) ๋ณด๋‹ค๋Š” Thermometer.newInstance(TemperatureScale.CELSIUS) ๊ฐ€ ํ•˜๋Š” ์ผ์„ ํ›จ์”ฌ ๋ช…ํ™•ํžˆ ์•Œ๋ ค์คŒ.


๐Ÿ’ก ๋‹ค์ค‘์ •์˜๋Š” ์‹ ์ค‘ํžˆ ์‚ฌ์šฉํ•˜๋ผ

โ€œํ”„๋กœ๊ทธ๋ž˜๋ฐ ์–ธ์–ด๊ฐ€ ๋‹ค์ค‘์ •์˜๋ฅผ ํ—ˆ์šฉํ•œ๋‹ค๊ณ  ํ•ด์„œ ๋‹ค์ค‘์ •์˜๋ฅผ ๊ผญ ํ™œ์šฉํ•˜๋ผ๋Š” ๋œป์€ ์•„๋‹ˆ๋‹คโ€

1. ๋‹ค์ค‘์ •์˜ ๋ฉ”์„œ๋“œ ์„ ํƒ ์‹œ์ 

// ์ปฌ๋ ‰์…˜ ๋ถ„๋ฅ˜๊ธฐ - ์˜ค๋ฅ˜! ์ด ํ”„๋กœ๊ทธ๋žจ์€ ๋ฌด์—‡์„ ์ถœ๋ ฅํ• ๊นŒ?
public class CollectionClassifier {
    public static String classify(Set<?> s) {
        return "์ง‘ํ•ฉ";
    }

    public static String classify(List<?> lst) {
        return "๋ฆฌ์ŠคํŠธ";
    }

    public static String classify(Collection<?> c) {
        return "๊ทธ ์™ธ";
    }

    public static void main(String[] args) {
        Collection<?>[] collections = {
                new HashSet<String>(),
                new ArrayList<BigInteger>(),
                new HashMap<String, String>().values()
        };

        for (Collection<?> c : collections)
            System.out.println(classify(c));
    }
}
  • ์œ„ ํ”„๋กœ๊ทธ๋žจ์€ ๋ฌด์—‡์„ ์ถœ๋ ฅํ• ๊นŒ?
    • โ€œ์ง‘ํ•ฉโ€, โ€œ๋ฆฌ์ŠคํŠธโ€, โ€œ๊ทธ ์™ธโ€๋ฅผ ์ถœ๋ ฅํ•  ๊ฒƒ์œผ๋กœ ์˜ˆ์ƒ.
  • ์ด์ƒํ•˜๊ฒŒ๋„ ์œ„ ํ”„๋กœ๊ทธ๋žจ์€ โ€œ๊ทธ์™ธโ€๋งŒ ์„ธ๋ฒˆ ์—ฐ๋‹ฌ์•„ ์ถœ๋ ฅํ•œ๋‹ค.
  • ์ด์œ  : ๋‹ค์ค‘์ •์˜ ๋ฉ”์„œ๋“œ์˜ ์„ ํƒ์€ ์ปดํŒŒ์ผํƒ€์ž„์— ์˜ค์ง ๋งค๊ฐœ๋ณ€์ˆ˜์˜ ์ปดํŒŒ์ผํƒ€์ž„ ํƒ€์ž…์— ์˜ํ•ด ์ด๋ค„์ง€๊ธฐ ๋•Œ๋ฌธ
  • ์ฆ‰, main๋ฉ”์„œ๋“œ์—์„œ for๋ฌธ ์•ˆ์˜ c๋Š” ํ•ญ์ƒ Collection<?>ํƒ€์ž…์ด๋ฏ€๋กœ ํ•ญ์ƒ ์„ธ ๋ฒˆ์งธ classify(Collection<?> c)๊ฐ€ ํ˜ธ์ถœ๋œ ๊ฒƒ.
  • ์˜๋„๋Œ€๋กœ ๋™์ž‘์‹œํ‚ค๋ ค๋ฉด ์•„๋ž˜ ์ฝ”๋“œ์ฒ˜๋Ÿผ classify ๋ฉ”์„œ๋“œ๋ฅผ ํ•˜๋‚˜๋กœ ํ•ฉ์นœ ํ›„ instanceof๋กœ ๊ฒ€์‚ฌํ•˜๋ฉด ๋จ
public static String classify(Collection<?> c) {
    return c instanceof Set  ? "์ง‘ํ•ฉ" :
            c instanceof List ? "๋ฆฌ์ŠคํŠธ" : "๊ทธ ์™ธ";
}

2. ๋‹ค์ค‘์ •์˜ ์ฃผ์˜์ 

  • ๋‹ค์ค‘์ •์˜๊ฐ€ ํ˜ผ๋™์„ ์ผ์œผํ‚ค๋Š” ์ƒํ™ฉ์„ ํ”ผํ•ด์•ผ ํ•œ๋‹ค.
    • API ์‚ฌ์šฉ์ž๊ฐ€ ๋งค๊ฐœ๋ณ€์ˆ˜๋ฅผ ๋„˜๊ธฐ๋ฉด์„œ ์–ด๋–ค ๋‹ค์ค‘์ •์˜ ๋ฉ”์„œ๋“œ๊ฐ€ ํ˜ธ์ถœ๋ ์ง€๋ฅผ ๋ชจ๋ฅธ๋‹ค๋ฉด ํ”„๋กœ๊ทธ๋žจ์ด ์˜ค๋™์ž‘ํ•˜๊ธฐ ์‰ฝ๋‹ค.
  • ์•ˆ์ „ํ•˜๊ณ  ๋ณด์ˆ˜์ ์œผ๋กœ ๊ฐ€๋ ค๋ฉด ๋งค๊ฐœ๋ณ€์ˆ˜ ์ˆ˜๊ฐ€ ๊ฐ™์€ ๋‹ค์ค‘์ •์˜๋Š” ๋งŒ๋“ค์ง€ ๋ง์ž
    • ๋‹ค์ค‘์ •์˜ํ•˜๋Š” ๋Œ€์‹  ๋ฉ”์„œ๋“œ ์ด๋ฆ„์„ ๋‹ค๋ฅด๊ฒŒ ์ง€์–ด์ฃผ๋Š” ๊ธธ๋„ ํ•ญ์ƒ ์—ด๋ ค ์žˆ์Œ.
  • ๋ฉ”์„œ๋“œ๋ฅผ ๋‹ค์ค‘์ •์˜ํ•  ๋•Œ, ์„œ๋กœ ๋‹ค๋ฅธ ํ•จ์ˆ˜ํ˜• ์ธํ„ฐํŽ˜์ด์Šค๋ผ๋„ ๊ฐ™์€ ์œ„์น˜์˜ ์ธ์ˆ˜๋กœ ๋ฐ›์•„์„œ๋Š” ์•ˆ ๋œ๋‹ค.
    • ์„œ๋กœ ๋‹ค๋ฅธ ํ•จ์ˆ˜ํ˜• ์ธํ„ฐํŽ˜์ด์Šค๋ผ๋„ ์„œ๋กœ ๊ทผ๋ณธ์ ์œผ๋กœ ๋‹ค๋ฅด์ง€ ์•Š์Œ.


๐Ÿ’ก ๊ฐ€๋ณ€์ธ์ˆ˜๋Š” ์‹ ์ค‘ํžˆ ์‚ฌ์šฉํ•˜๋ผ

โ€œ๋ฉ”์„œ๋“œ ์ •์˜ ์‹œ ํ•„์ˆ˜ ๋งค๊ฐœ๋ณ€์ˆ˜๋Š” ๊ฐ€๋ณ€์ธ์ˆ˜ ์•ž์— ๋‘๊ณ , ๊ฐ€๋ณ€์ธ์ˆ˜๋ฅผ ์‚ฌ์šฉํ•  ๋•Œ๋Š” ์„ฑ๋Šฅ ๋ฌธ์ œ๊นŒ์ง€ ๊ณ ๋ คํ•˜์žโ€

1. ๊ฐ„๋‹จํ•œ ๊ฐ€๋ณ€์ธ์ˆ˜ ํ™œ์šฉ ์˜ˆ์‹œ

// ๊ฐ„๋‹จํ•œ ๊ฐ€๋ณ€์ธ์ˆ˜ ํ™œ์šฉ ์˜ˆ
static int sum(int... args) {
    int sum = 0;
    for (int arg : args)
        sum += arg;
    return sum;
}
  • ์œ„ ์ฝ”๋“œ๋Š” ์ž…๋ ฅ๋ฐ›์€ int ์ธ์ˆ˜๋“ค์˜ ํ•ฉ์„ ๊ณ„์‚ฐํ•ด์ฃผ๋Š” ๊ฐ€๋ณ€์ธ์ˆ˜ ๋ฉ”์„œ๋“œ์ž„.(์ธ์ˆ˜๊ฐ€ 0๊ฐœ์—ฌ๋„ ๋จ)

2. ์ธ์ˆ˜๊ฐ€ 1๊ฐœ ์ด์ƒ์ผ ๋•Œ

  • ์ž˜๋ชป๋œ ์˜ˆ์‹œ
// ์ธ์ˆ˜๊ฐ€ 1๊ฐœ ์ด์ƒ์ด์–ด์•ผ ํ•˜๋Š” ๊ฐ€๋ณ€์ธ์ˆ˜ ๋ฉ”์„œ๋“œ - ์ž˜๋ชป ๊ตฌํ˜„ํ•œ ์˜ˆ!
static int min(int... args) {
    if (args.length == 0)
        throw new IllegalArgumentException("์ธ์ˆ˜๊ฐ€ 1๊ฐœ ์ด์ƒ ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค.");
    int min = args[0];
    for (int i = 1; i < args.length; i++)
        if (args[i] < min)
            min = args[i];
    return min;
}
  • ์œ„ ์ฝ”๋“œ์˜ ๋ฌธ์ œ์ 
    1. ์ธ์ˆ˜๋ฅผ 0๊ฐœ๋งŒ ๋„ฃ์–ด ํ˜ธ์ถœํ•˜๋ฉด (์ปดํŒŒ์ผํƒ€์ž„์ด ์•„๋‹Œ) ๋Ÿฐํƒ€์ž„์— ์‹คํŒจ ํ•จ.
    2. ์ฝ”๋“œ๋„ ์ง€์ €๋ถ„ํ•จ. args ์œ ํšจ์„ฑ ๊ฒ€์‚ฌ๋ฅผ ๋ช…์‹œ์ ์œผ๋กœ ํ•ด์•ผํ•จ.
  • ์˜ฌ๋ฐ”๋ฅธ ์˜ˆ์‹œ
// ์ธ์ˆ˜๊ฐ€ 1๊ฐœ ์ด์ƒ์ด์–ด์•ผ ํ•  ๋•Œ ๊ฐ€๋ณ€์ธ์ˆ˜๋ฅผ ์ œ๋Œ€๋กœ ์‚ฌ์šฉํ•˜๋Š” ๋ฐฉ๋ฒ•
static int min(int firstArg, int... remainingArgs) {
    int min = firstArg;
    for (int arg : remainingArgs)
        if (arg < min)
            min = arg;
    return min;
}
  • ์ฒซ ๋ฒˆ์งธ๋กœ๋Š” ํ‰๋ฒ”ํ•œ ๋งค๊ฐœ๋ณ€์ˆ˜๋ฅผ ๋ฐ›๊ณ , ๋‘ ๋ฒˆ์งธ๋กœ ๊ฐ€๋ณ€์ธ์ˆ˜๋ฅผ ๋ฐ›์œผ๋ฉด ์ž˜๋ชป๋œ ์˜ˆ์‹œ์˜ ๋ฌธ์ œ์ ๋“ค์ด ๋ง๋”ํžˆ ํ•ด๊ฒฐ๋จ.

3. ์„ฑ๋Šฅ ์ตœ์ ํ™”

  • ์˜ˆ์‹œ) ๋ฉ”์„œ๋“œ ํ˜ธ์ถœ์˜ 95%๊ฐ€ ์ธ์ˆ˜๋ฅผ 3๊ฐœ ์ดํ•˜๋กœ ์‚ฌ์šฉํ•˜๋Š” ์ƒํ™ฉ

โ†’ ์•„๋ž˜์™€ ๊ฐ™์ด ์ธ์ˆ˜๊ฐ€ 0๊ฐœ์ธ ๊ฒƒ๋ถ€ํ„ฐ 4๊ฐœ์ธ ๊ฒƒ๊นŒ์ง€, 5๊ฐœ๋ฅผ ๋‹ค์ค‘์ •์˜

public void foo() {}
public void foo(int a1) {}
public void foo(int a1,int a2) {}
public void foo(int a1, int a2, int a3) {}
public void foo(int a1, int a2, int a3, int... rest) {}
  • ์œ„์™€ ๊ฐ™์ด ๊ตฌํ˜„ํ•˜๋ฉด ๋งˆ์ง€๋ง‰ ๋‹ค์ค‘์ •์˜ ๋ฉ”์„œ๋“œ๊ฐ€ ์ธ์ˆ˜ 4๊ฐœ ์ด์ƒ์ธ 5%์˜ ํ˜ธ์ถœ์„ ๋‹ด๋‹นํ•จ

โ†’ ๋ฉ”์„œ๋“œ ํ˜ธ์ถœ ์ค‘ ๋‹จ 5%๋งŒ์ด ๋ฐฐ์—ด์„ ์ƒ์„ฑํ•˜๊ฒŒ ๋จ

  • ๋Œ€๋‹ค์ˆ˜์˜ ์„ฑ๋Šฅ ์ตœ์ ํ™”์™€ ๋งˆ์ฐฌ๊ฐ€์ง€๋กœ ์ด ๊ธฐ๋ฒ•๋„ ๋ณดํ†ต ๋•Œ๋Š” ๋ณ„ ์ด๋“์ด ์—†์ง€๋งŒ, ๊ผญ ํ•„์š”ํ•œ ํŠน์ˆ˜ํ•œ ์ƒํ™ฉ์—์„œ ์‚ฌ๋ง‰์˜ ์˜ค์•„์‹œ์Šค๊ฐ€ ๋˜์–ด์ค„ ๊ฒƒ์ž„.


๐Ÿ’ก null์ด ์•„๋‹Œ, ๋นˆ ์ปฌ๋ ‰์…˜์ด๋‚˜ ๋ฐฐ์—ด์„ ๋ฐ˜ํ™˜ํ•˜๋ผ

โ€œnull์„ ๋ฐ˜ํ™˜ํ•˜๋Š” API๋Š” ์‚ฌ์šฉํ•˜๊ธฐ ์–ด๋ ต๊ณ  ์˜ค๋ฅ˜์ฒ˜๋ฆฌ ์ฝ”๋“œ๋„ ๋Š˜์–ด๋‚œ๋‹คโ€

1. null์„ ๋ฐ˜ํ™˜

// ์žฌ๊ณ ๊ฐ€ ํ•˜๋‚˜๋„ ์—†์„ ๋•Œ null์„ ๋ฐ˜ํ™˜ํ•˜๋Š” ์˜ˆ
public List<Cheese> getCheeses() {
		return cheesesInStock.isEmpty() ? null
				: new ArrayList<>(cheesesInStock);
}
  • ์ด ์ฝ”๋“œ์ฒ˜๋Ÿผ null์„ ๋ฐ˜ํ™˜ํ•œ๋‹ค๋ฉด, ํด๋ผ์ด์–ธํŠธ๋Š” ์ด null ์ƒํ™ฉ์„ ์ฒ˜๋ฆฌํ•˜๋Š” ์ฝ”๋“œ๋ฅผ ์•„๋ž˜์ฒ˜๋Ÿผ ์ถ”๊ฐ€๋กœ ์ž‘์„ฑํ•ด์•ผ ํ•จ
List<Cheese> cheeses = shop.getCheeses();
if(cheeses != null && cheeses.contains(Cheese.STILTON))
		System.out.println("์ข‹์•˜์–ด, ๋ฐ”๋กœ ๊ทธ๊ฑฐ์•ผ.");
  • ํด๋ผ์ด์–ธํŠธ๋Š” cheeses != null ์ฒ˜๋Ÿผ ๋ฐฉ์–ด์ฝ”๋“œ๋ฅผ ํ•ญ์ƒ ์ž‘์„ฑํ•ด์ค˜์•ผ ํ•จ.

2. ๋นˆ ์ปฌ๋ ‰์…˜์„ ๋ฐ˜ํ™˜

// ๋นˆ ์ปฌ๋ ‰์…˜์„ ๋ฐ˜ํ™˜ํ•˜๋Š” ์˜ฌ๋ฐ”๋ฅธ ์˜ˆ
public List<Cheese> getCheeses() {
		return new ArrayList<>(cheesesInStock);
}
  • ์‚ฌ์šฉ ํŒจํ„ด์— ๋”ฐ๋ผ ๋นˆ ์ปฌ๋ ‰์…˜ ํ• ๋‹น์ด ์„ฑ๋Šฅ ์ €ํ•˜์˜ ์ฃผ๋ฒ”์ด ๋˜๋Š” ๊ฒฝ์šฐ๋Š” ์–ด๋–ป๊ฒŒ ํ•˜์ง€?
    • Collections.emptyList , Collections.emptySet ๊ณผ ๊ฐ™์€ ๋นˆ ๋ถˆ๋ณ€ ์ปฌ๋ ‰์…˜์„ ๋ฐ˜ํ™˜ํ•˜๋ฉด ๋จ
  • Collections.emptyList ์‚ฌ์šฉ ์˜ˆ์‹œ
// ์ตœ์ ํ™” - ๋นˆ ์ปฌ๋ ‰์…˜์„ ๋งค๋ฒˆ ์ƒˆ๋กœ ํ• ๋‹นํ•˜์ง€ ์•Š๋„๋ก ํ•จ.
public List<Cheese> getCheeses() {
		return cheesesInStock.isEmpty() ? Collections.emptyList()
				: new ArrayList<>(cheesesInStock);
}
  • ๋ฐฐ์—ด์„ ์“ธ ๋•Œ๋„ ๋งˆ์ฐฌ๊ฐ€์ง€์ž„

โ†’ ์ ˆ๋Œ€ null์„ ๋ฐ˜ํ™˜ํ•˜์ง€ ๋ง๊ณ  ๊ธธ์ด๊ฐ€ 0์ธ ๋ฐฐ์—ด์„ ๋ฐ˜ํ™˜ํ•˜๋ผ

// ๊ธธ์ด๊ฐ€ 0์ผ ์ˆ˜๋„ ์žˆ๋Š” ๋ฐฐ์—ด์„ ๋ฐ˜ํ™˜ํ•˜๋Š” ์˜ฌ๋ฐ”๋ฅธ ๋ฐฉ๋ฒ•
public Cheese[] getCheeses() {
		return cheesesInStock.toArray(new Cheeses[0]);
}
  • ์ด ๋ฐฉ์‹์ด ์„ฑ๋Šฅ์„ ๋–จ์–ด๋œจ๋ฆด ๊ฒƒ ๊ฐ™๋‹ค๋ฉด ๊ธธ์ด 0์งœ๋ฆฌ ๋ฐฐ์—ด์„ ๋ฏธ๋ฆฌ ์„ ์–ธํ•ด๋‘๊ณ  ๋ฐ˜ํ™˜ํ•˜๋ฉด ๋จ.


๐Ÿ’ก ์˜ต์…”๋„ ๋ฐ˜ํ™˜์€ ์‹ ์ค‘ํžˆ ํ•˜๋ผ

โ€œ์˜ต์…”๋„ ๋ฐ˜ํ™˜์—๋Š” ์„ฑ๋Šฅ ์ €ํ•˜๊ฐ€ ๋’ค๋”ฐ๋ฅด๋‹ˆ, ์„ฑ๋Šฅ์ด ๋ฏผ๊ฐํ•œ ๋ฉ”์„œ๋“œ๋ผ๋ฉด null ์„ ๋ฐ˜ํ™˜ํ•˜๊ฑฐ๋‚˜ ์˜ˆ์™ธ๋ฅผ ๋˜์ง€๋Š” ํŽธ์ด ๋‚˜์„ ์ˆ˜ ์žˆ๋‹คโ€

1. Optional

  • Optional<T>๋Š” null์ด ์•„๋‹Œ T ํƒ€์ž… ์ฐธ์กฐ๋ฅผ ํ•˜๋‚˜ ๋‹ด๊ฑฐ๋‚˜, ํ˜น์€ ์•„๋ฌด๊ฒƒ๋„ ๋‹ด์ง€ ์•Š์„ ์ˆ˜ ์žˆ์Œ
  • โ€˜๋น„์—ˆ๋‹คโ€™ : ์•„๋ฌด๊ฒƒ๋„ ๋‹ด์ง€ ์•Š์€ ์˜ต์…”๋„
  • โ€˜๋น„์ง€ ์•Š์•˜๋‹คโ€™ : ์–ด๋–ค ๊ฐ’์„ ๋‹ด์€ ์˜ต์…”๋„
  • ์˜ต์…”๋„์€ ์›์†Œ๋ฅผ ์ตœ๋Œ€ 1๊ฐœ ๊ฐ€์งˆ ์ˆ˜ ์žˆ๋Š” ๋ถˆ๋ณ€ ์ปฌ๋ ‰์…˜์ž„
  • ์˜ต์…”๋„์„ ๋ฐ˜ํ™˜ํ•˜๋Š” ๋ฉ”์„œ๋“œ๋Š” ์˜ˆ์™ธ๋ฅผ ๋˜์ง€๋Š” ๋ฉ”์„œ๋“œ๋ณด๋‹ค ์œ ์—ฐํ•˜๊ณ  ์‚ฌ์šฉํ•˜๊ธฐ ์‰ฌ์šฐ๋ฉฐ, null์„ ๋ฐ˜ํ™˜ํ•˜๋Š” ๋ฉ”์„œ๋“œ๋ณด๋‹ค ์˜ค๋ฅ˜ ๊ฐ€๋Šฅ์„ฑ์ด ์ž‘๋‹ค

2. ์˜ต์…”๋„ ๋ฐ˜ํ™˜ ์˜ˆ์‹œ

// ์ปฌ๋ ‰์…˜์—์„œ ์ตœ๋Œ“๊ฐ’์„ ๊ตฌํ•ด Optional<E>๋กœ ๋ฐ˜ํ™˜ํ•œ๋‹ค. 
public static <E extends Comparable<E>>
Optional<E> max(Collection<E> c) {
    if (c.isEmpty())
        return Optional.empty();

    E result = null;
    for (E e : c)
        if (result == null || e.compareTo(result) > 0)
            result = Objects.requireNonNull(e);

    return Optional.of(result);
}
  • Optional.empty() : ๋นˆ ์˜ต์…”๋„ ์ƒ์„ฑ
  • Optional.of(value) : ๊ฐ’์ด ๋“  ์˜ต์…”๋„ ์ƒ์„ฑ
    • value ํŒŒ๋ผ๋ฏธํ„ฐ์— null์„ ๋„˜๊ธฐ๋ฉด NullPointerException์„ ๋˜์ง€๋‹ˆ ์ฃผ์˜ํ•˜์ž
  • Optional.ofNullable(value) : null ๊ฐ’๋„ ํ—ˆ์šฉํ•˜๋Š” ์˜ต์…”๋„ ์ƒ์„ฑ
  • ์ŠคํŠธ๋ฆผ์˜ ์ข…๋‹จ ์—ฐ์‚ฐ ์ค‘ ์ƒ๋‹น์ˆ˜๊ฐ€ ์˜ต์…”๋„์„ ๋ฐ˜ํ™˜ ํ•จ.

โ†’ ์œ„์˜ ๋ฉ”์„œ๋“œ๋ฅผ ์•„๋ž˜ ์ฝ”๋“œ์ฒ˜๋Ÿผ ๋ฆฌํŒฉํ„ฐ๋งํ•  ์ˆ˜ ์žˆ์Œ.

// ์ปฌ๋ ‰์…˜์—์„œ ์ตœ๋Œ“๊ฐ’์„ ๊ตฌํ•ด Optional<E>๋กœ ๋ฐ˜ํ™˜ํ•œ๋‹ค. - ์ŠคํŠธ๋ฆผ ๋ฒ„์ „
public static <E extends Comparable<E>>
Optional<E> max(Collection<E> c) {
    return c.stream().max(Comparator.naturalOrder());
}

3. ์˜ต์…”๋„ ํ™œ์šฉ

  • ๊ธฐ๋ณธ๊ฐ’์„ ์„ค์ •ํ•˜๋Š” ๋ฐฉ๋ฒ•
// ๊ธฐ๋ณธ ๊ฐ’์„ ์ •ํ•ด๋‘˜ ์ˆ˜ ์žˆ์Œ
String lastWordInLexicon = max(words).orElse("๋‹จ์–ด ์—†์Œ...");
  • ์›ํ•˜๋Š” ์˜ˆ์™ธ๋ฅผ ๋˜์ง€๋Š” ๋ฐฉ๋ฒ•
Toy myToy = max(toys).orElseThrow(TemperTantrumException::new)
  • ํ•ญ์ƒ ๊ฐ’์ด ์ฑ„์›Œ์ ธ ์žˆ๋‹ค๊ณ  ๊ฐ€์ •
Element lastNobleFas = max(Elements.NOBLE_GASES).get();
  • isPresent() : ์˜ต์…”๋„์ด ์ฑ„์›Œ์ ธ ์žˆ์œผ๋ฉด true, ๋น„์–ด ์žˆ์œผ๋ฉด false๋ฅผ ๋ฐ˜ํ™˜

4. ์˜ต์…”๋„ ์‚ฌ์šฉ ๊ทœ์น™

  • ์–ด๋–ค ๊ฒฝ์šฐ์— ๋ฉ”์„œ๋“œ ๋ฐ˜ํ™˜ ํƒ€์ž… T ๋Œ€์‹  Optional<T> ๋กœ ์„ ์–ธํ•ด์•ผ ํ• ๊นŒ?

โ†’ ๊ธฐ๋ณธ ๊ทœ์น™ : ๊ฒฐ๊ณผ๊ฐ€ ์—†์„ ์ˆ˜ ์žˆ์œผ๋ฉฐ, ํด๋ผ์ด์–ธํŠธ๊ฐ€ ์ด ์ƒํ™ฉ์„ ํŠน๋ณ„ํ•˜๊ฒŒ ์ฒ˜๋ฆฌํ•ด์•ผ ํ•œ๋‹ค๋ฉด Optional<T>๋ฅผ ๋ฐ˜ํ™˜

  • ์ปฌ๋ ‰์…˜, ์ŠคํŠธ๋ฆผ, ๋ฐฐ์—ด ๊ฐ™์€ ์ปจํ…Œ์ด๋„ˆ ํƒ€์ž…์€ ์˜ต์…”๋„๋กœ ๊ฐ์‹ธ๋ฉด ์•ˆ ๋จ.
    • ex) Optional<List<T>>๋ฅผ ๋ฐ˜ํ™˜ํ•˜์ง€ ๋ง๊ณ  List<T>๋ฅผ ๋ฐ˜ํ™˜ํ•˜์ž
    • ๋นˆ ์ปจํ…Œ์ด๋„ˆ๋ฅผ ๊ทธ๋Œ€๋กœ ๋ฐ˜ํ™˜ํ•˜๋ฉด ํด๋ผ์ด์–ธํŠธ์— ์˜ต์…”๋„ ์ฒ˜๋ฆฌ์ฝ”๋“œ๋ฅผ ๋„ฃ์ง€ ์•Š์•„๋„ ๋จ.
  • ๋ฐ•์‹ฑ๋œ ๊ธฐ๋ณธ ํƒ€์ž…์„ ๋‹ด์€ ์˜ต์…”๋„์„ ๋ฐ˜ํ™˜ํ•˜๋Š” ์ผ์€ ์—†๋„๋ก ํ•˜์ž.
    • ๋ฐ•์‹ฑ๋œ ๊ธฐ๋ณธ ํƒ€์ž…์„ ๋‹ด๋Š” ์˜ต์…”๋„์€ ๊ธฐ๋ณธ ํƒ€์ž…๋ณด๋‹ค ๋‘ ๊ฒน์ด๋‚˜ ๊ฐ’์„ ๊ฐ์‹ธ์„œ ๋ฌด๊ฑฐ์šธ ์ˆ˜ ๋ฐ–์— ์—†์Œ.
    • ๋Œ€์ฒด์ฑ„๋กœ int, long, double ์ „์šฉ ์˜ต์…”๋„ ํด๋ž˜์Šค๋“ค์ด ์žˆ์Œ
      • OptionalInt, OptionalLong, OptionalDouble
  • ์˜ต์…”๋„์„ ์ปฌ๋ ‰์…˜์˜ ํ‚ค, ๊ฐ’, ์›์†Œ๋‚˜ ๋ฐฐ์—ด์˜ ์›์†Œ๋กœ ์‚ฌ์šฉํ•˜๋Š” ๊ฒŒ ์ ์ ˆํ•œ ์ƒํ™ฉ์€ ๊ฑฐ์˜ ์—†๋‹ค.
    • ex) ๋งต์˜ ํ‚ค๋กœ ์˜ต์…”๋„์„ ์‚ฌ์šฉํ•˜๋Š” ๊ฒฝ์šฐ, ๋งต ์•ˆ์— ํ‚ค๊ฐ€ ์—†๋‹ค๋Š” ์‚ฌ์‹ค์„ ๋‚˜ํƒ€๋‚ด๋Š” ๋ฐฉ๋ฒ•์ด ๋‘ ๊ฐ€์ง€๊ฐ€ ๋จ. โ†’ ์“ธ๋ฐ์—†์ด ๋ณต์žก์„ฑ๋งŒ ๋†’์—ฌ์„œ ํ˜ผ๋ž€๊ณผ ์˜ค๋ฅ˜ ๊ฐ€๋Šฅ์„ฑ์„ ํ‚ค์šธ ๋ฟ์ž„.
  • ์˜ต์…”๋„ ๋ฐ˜ํ™˜์˜ ์„ฑ๋Šฅ ์ €ํ•˜
    • Optional ๋„ ์—„์—ฐํžˆ ์ƒˆ๋กœ ํ• ๋‹นํ•˜๊ณ  ์ดˆ๊ธฐํ™”ํ•ด์•ผ ํ•˜๋Š” ๊ฐ์ฒด์ด๊ณ , ๊ทธ ์•ˆ์—์„œ ๊ฐ’์„ ๊บผ๋‚ด๋ ค๋ฉด ๋ฉ”์„œ๋“œ๋ฅผ ํ˜ธ์ถœํ•ด์•ผ ํ•จ.
    • ์„ฑ๋Šฅ์ด ์ค‘์š”ํ•œ ์ƒํ™ฉ์—์„œ๋Š” ์˜ต์…”๋„๋ณด๋‹ค๋Š” null์„ ๋ฐ˜ํ™˜ํ•˜๊ฑฐ๋‚˜ ์˜ˆ์™ธ๋ฅผ ๋˜์ง€๋Š” ํŽธ์ด ๋‚˜์„ ์ˆ˜ ์žˆ์Œ


๐Ÿ’ก ๊ณต๊ฐœ๋œ API ์š”์†Œ์—๋Š” ํ•ญ์ƒ ๋ฌธ์„œํ™” ์ฃผ์„์„ ์ž‘์„ฑํ•˜๋ผ

โ€œ๋ฌธ์„œํ™” ์ฃผ์„์€ API๋ฅผ ๋ฌธ์„œํ™”ํ•˜๋Š” ๊ฐ€์žฅ ํ›Œ๋ฅญํ•˜๊ณ  ํšจ๊ณผ์ ์ธ ๋ฐฉ๋ฒ•โ€

1. ์ž๋ฐ”๋…(Javadoc) ์œ ํ‹ธ๋ฆฌํ‹ฐ

  • ์ž๋ฐ”๋…์€ ์†Œ์Šค์ฝ”๋“œ ํŒŒ์ผ์—์„œ ๋ฌธ์„œํ™” ์ฃผ์„(doc comment; ์ž๋ฐ”๋… ์ฃผ์„)์ด๋ผ๋Š” ํŠน์ˆ˜ํ•œ ํ˜•ํƒœ๋กœ ๊ธฐ์ˆ ๋œ ์„ค๋ช…์„ ์ถ”๋ ค API๋กœ ๋ฌธ์„œ๋กœ ๋ณ€ํ™˜ํ•ด ์คŒ.
  • How to Write Doc Comments for the Javadoc Tool

2. ๋ฌธ์„œํ™” ์ฃผ์„ ์ง€์นจ

  • API๋ฅผ ์˜ฌ๋ฐ”๋ฅด๊ฒŒ ๋ฌธ์„œํ™”ํ•˜๋ ค๋ฉด ๊ณต๊ฐœ๋œ ๋ชจ๋“  ํด๋ž˜์Šค, ์ธํ„ฐํŽ˜์ด์Šค, ๋ฉ”์„œ๋“œ, ํ•„๋“œ ์„ ์–ธ์— ๋ฌธ์„œํ™” ์ฃผ์„์„ ๋‹ฌ์•„์•ผ ํ•จ.
  • ๋ฉ”์„œ๋“œ์šฉ ๋ฌธ์„œํ™” ์ฃผ์„์—๋Š” ํ•ด๋‹น ๋ฉ”์„œ๋“œ์™€ ํด๋ผ์ด์–ธํŠธ ์‚ฌ์ด์˜ ๊ทœ์•ฝ์„ ๋ช…๋ฃŒํ•˜๊ฒŒ ๊ธฐ์ˆ ํ•ด์•ผ ํ•จ.
  • how(๋ฉ”์„œ๋“œ๊ฐ€ ์–ด๋–ป๊ฒŒ ๋™์ž‘ํ•˜๋Š”์ง€)๊ฐ€ ์•„๋‹ˆ๋ผ what(๋ฌด์—‡์„ ํ•˜๋Š”์ง€)๋ฅผ ๊ธฐ์ˆ ํ•ด์•ผ ํ•จ
  • ๋ฉ”์„œ๋“œ๋ฅผ ํ˜ธ์ถœํ•˜๊ธฐ ์œ„ํ•œ ์ „์ œ์กฐ๊ฑด(precondition)์„ ๋ชจ๋‘ ๋‚˜์—ดํ•ด์•ผ ํ•จ.
    • ์ผ๋ฐ˜์ ์œผ๋กœ ์ „์ œ์กฐ๊ฑด์€ @throw ํƒœ๊ทธ๋กœ ๋น„๊ฒ€์‚ฌ ์˜ˆ์™ธ๋ฅผ ์„ ์–ธํ•˜์—ฌ ์•”์‹œ์ ์œผ๋กœ ๊ธฐ์ˆ ํ•จ
    • @param ํƒœ๊ทธ๋ฅผ ์ด์šฉํ•ด ๊ทธ ์กฐ๊ฑด์— ์˜ํ–ฅ๋ฐ›๋Š” ๋งค๊ฐœ๋ณ€์ˆ˜์— ๊ธฐ์ˆ ํ•  ์ˆ˜๋„ ์žˆ์Œ
  • ๋ฉ”์„œ๋“œ๊ฐ€ ์„ฑ๊ณต์ ์œผ๋กœ ์ˆ˜ํ–‰๋œ ํ›„ ๋งŒ์กฑํ•ด์•ผ ํ•˜๋Š” ์‚ฌํ›„์กฐ๊ฑด(postcondition)๋„ ๋ชจ๋‘ ๋‚˜์—ดํ•ด์•ผ ํ•จ.
  • ๋ถ€์ž‘์šฉ๋„ ๋ฌธ์„œํ™”ํ•ด์•ผ ํ•จ.
    • ๋ถ€์ž‘์šฉ : ์‚ฌํ›„์กฐ๊ฑด์œผ๋กœ ๋ช…ํ™•ํžˆ ๋‚˜ํƒ€๋‚˜์ง€๋Š” ์•Š์ง€๋งŒ ์‹œ์Šคํ…œ์˜ ์ƒํƒœ์— ์–ด๋– ํ•œ ๋ณ€ํ™”๋ฅผ ๊ฐ€์ ธ์˜ค๋Š” ๊ฒƒ
    • ex) ๋ฐฑ๊ทธ๋ผ์šด๋“œ ์Šค๋ ˆ๋“œ๋ฅผ ์‹œ์ž‘์‹œํ‚ค๋Š” ๋ฉ”์„œ๋“œ
  • ๋ฉ”์„œ๋“œ์˜ ๊ณ„์•ฝ(contract)์„ ์™„๋ฒฝํžˆ ๊ธฐ์ˆ ํ•˜๋ ค๋ฉด ๋ชจ๋“  ๋งค๊ฐœ๋ณ€์ˆ˜์— @param ํƒœ๊ทธ๋ฅผ, ๋ฐ˜ํ™˜ ํƒ€์ž…์ด void๊ฐ€ ์•„๋‹ˆ๋ผ๋ฉด @return ํƒœ๊ทธ๋ฅผ, ๋ฐœ์ƒํ•  ๊ฐ€๋Šฅ์„ฑ์ด ์žˆ๋Š” (๊ฒ€์‚ฌ๋“  ๋น„๊ฒ€์‚ฌ๋“ ) ๋ชจ๋“  ์˜ˆ์™ธ์— @thorw ํƒœ๊ทธ๋ฅผ ๋‹ฌ์•„์•ผ ํ•œ๋‹ค.
  • ํƒœ๊ทธ ์‚ฌ์šฉ ๊ด€๋ก€
    • ๊ด€๋ก€์ƒ @param ํƒœ๊ทธ์™€ @return ํƒœ๊ทธ์˜ ์„ค๋ช…์€ ํ•ด๋‹น ๋งค๊ฐœ๋ณ€์ˆ˜๊ฐ€ ๋œปํ•˜๋Š” ๊ฐ’์ด๋‚˜ ๋ฐ˜ํ™˜๊ฐ’์„ ์„ค๋ช…ํ•˜๋Š” ๋ช…์‚ฌ๊ตฌ๋ฅผ ์‚ฌ์šฉํ•จ.
    • ๊ด€๋ก€์ƒ @param , @return, @throws ํƒœ๊ทธ์˜ ์„ค๋ช…์—๋Š” ๋งˆ์นจํ‘œ๋ฅผ ๋ถ™์ด์ง€ ์•Š์Œ
  • {@code} ํƒœ๊ทธ
    1. ํƒœ๊ทธ๋กœ ๊ฐ์‹ผ ๋‚ด์šฉ์„ ์ฝ”๋“œ์šฉ ํฐํŠธ๋กœ ๋ Œ๋”๋ง
    2. ํƒœ๊ทธ๋กœ ๊ฐ์‹ผ ๋‚ด์šฉ์— ํฌํ•จ๋œ HTML์š”์†Œ๋‚˜ ๋‹ค๋ฅธ ์ž๋ฐ”๋… ํƒœ๊ทธ๋ฅผ ๋ฌด์‹œํ•จ.
    • ์—ฌ๋Ÿฌ ์ค„๋กœ ๋œ ์ฝ”๋“œ ์˜ˆ์‹œ๋ฅผ ๋„ฃ์œผ๋ ค๋ฉด <pre>{@code ... ์ฝ”๋“œ ... }</pre>์ฒ˜๋Ÿผ ์‚ฌ์šฉ
  • ์ž๊ธฐ์‚ฌ์šฉ ํŒจํ„ด์€ ์ž๋ฐ” 8์— ์ถ”๊ฐ€๋œ @implSpec ํƒœ๊ทธ๋กœ ๋ฌธ์„œํ™”ํ•œ๋‹ค.
  • API ์„ค๋ช…์— <, >, & ๋“ฑ์˜ HTML ๋ฉ”ํƒ€๋ฌธ์ž๋ฅผ ํฌํ•จ์‹œํ‚ค๋ ค๋ฉด {@literal} ํƒœ๊ทธ๋กœ ๊ฐ์‹ธ์ž
  • ํ•œ ํด๋ž˜์Šค(ํ˜น์€ ์ธํ„ฐํŽ˜์ด์Šค) ์•ˆ์—์„œ ์š”์•ฝ ์„ค๋ช…์ด ๋˜‘๊ฐ™์€ ๋ฉค๋ฒ„(ํ˜น์€ ์ƒ์„ฑ์ž)๊ฐ€ ๋‘˜ ์ด์ƒ์ด๋ฉด ์•ˆ ๋จ.
  • ํด๋ž˜์Šค, ์ธํ„ฐํŽ˜์ด์Šค, ํ•„๋“œ์˜ ์š”์•ฝ ์„ค๋ช…์€ ๋Œ€์ƒ์„ ์„ค๋ช…ํ•˜๋Š” ๋ช…์‚ฌ์ ˆ์ด์–ด์•ผ ํ•จ.
  • ์ œ๋„ค๋ฆญ ํƒ€์ž…์ด๋‚˜ ์ œ๋„ค๋ฆญ ๋ฉ”์„œ๋“œ๋ฅผ ๋ฌธ์„œํ™” ํ•  ๋•Œ๋Š” ๋ชจ๋“  ํƒ€์ž… ๋งค๊ฐœ๋ณ€์ˆ˜์— ์ฃผ์„์„ ๋‹ฌ์•„์•ผ ํ•จ.
  • ์—ด๊ฑฐ ํƒ€์ž…์„ ๋ฌธ์„œํ™”ํ•  ๋•Œ๋Š” ์ƒ์ˆ˜๋“ค์—๋„ ์ฃผ์„์„ ๋‹ฌ์•„์•ผ ํ•จ.
  • ์–ด๋…ธํ…Œ์ด์…˜ ํƒ€์ž…์„ ๋ฌธ์„œํ™”ํ•  ๋•Œ๋Š” ๋ฉค๋ฒ„๋“ค์—๋„ ๋ชจ๋‘ ์ฃผ์„์„ ๋‹ฌ์•„์•ผ ํ•จ.
  • ํŒจํ‚ค์ง€๋ฅผ ์„ค๋ช…ํ•˜๋Š” ๋ฌธ์„œํ™” ์ฃผ์„์€ package-info.java ํŒŒ์ผ์— ์ž‘์„ฑํ•œ๋‹ค.
  • ํด๋ž˜์Šค ํ˜น์€ ์ •์  ๋ฉ”์„œ๋“œ๊ฐ€ ์Šค๋ ˆ๋“œ ์•ˆ์ „ํ•˜๋“  ๊ทธ๋ ‡์ง€ ์•Š๋“ , ์Šค๋ ˆ๋“œ ์•ˆ์ „ ์ˆ˜์ค€์„ ๋ฐ˜๋“œ์‹œ API์„ค๋ช…์— ํฌํ•จํ•ด์•ผ ํ•œ๋‹ค.
  • {@inheritDoc} ํƒœ๊ทธ๋ฅผ ์‚ฌ์šฉํ•ด ์ƒ์œ„ ํƒ€์ž…์˜ ๋ฌธ์„œํ™” ์ฃผ์„ ์ผ๋ถ€๋ฅผ ์ƒ์†ํ•  ์ˆ˜ ์žˆ์Œ.

3. ๋ฌธ์„œํ™” ์ฃผ์„ ์‚ฌ์šฉ ์˜ˆ์‹œ

// ๋ฌธ์„œํ™” ์ฃผ์„ ์˜ˆ
public class DocExamples<E> {
    // ๋ฉ”์„œ๋“œ ์ฃผ์„ 
    /**
     * Returns the element at the specified position in this list.
     *
     * <p>This method is <i>not</i> guaranteed to run in constant
     * time. In some implementations it may run in time proportional
     * to the element position.
     *
     * @param  index index of element to return; must be
     *         non-negative and less than the size of this list
     * @return the element at the specified position in this list
     * @throws IndexOutOfBoundsException if the index is out of range
     *         ({@code index < 0 || index >= this.size()})
     */
    E get(int index) {
        return null;
    }
    // ํ•œ๊ธ€ ๋ฒ„์ „ 
    // /**
    //  * ์ด ๋ฆฌ์ŠคํŠธ์—์„œ ์ง€์ •ํ•œ ์œ„์น˜์˜ ์›์†Œ๋ฅผ ๋ฐ˜ํ™˜ํ•œ๋‹ค.
    //  *
    //  * <p>์ด ๋ฉ”์„œ๋“œ๋Š” ์ƒ์ˆ˜ ์‹œ๊ฐ„์— ์ˆ˜ํ–‰๋จ์„ ๋ณด์žฅํ•˜์ง€ <i>์•Š๋Š”๋‹ค</i>. ๊ตฌํ˜„์— ๋”ฐ๋ผ
    //  * ์›์†Œ์˜ ์œ„์น˜์— ๋น„๋ก€ํ•ด ์‹œ๊ฐ„์ด ๊ฑธ๋ฆด ์ˆ˜๋„ ์žˆ๋‹ค.
    //  *
    //  * @param  index ๋ฐ˜ํ™˜ํ•  ์›์†Œ์˜ ์ธ๋ฑ์Šค; 0 ์ด์ƒ์ด๊ณ  ๋ฆฌ์ŠคํŠธ ํฌ๊ธฐ๋ณด๋‹ค ์ž‘์•„์•ผ ํ•œ๋‹ค.
    //  * @return ์ด ๋ฆฌ์ŠคํŠธ์—์„œ ์ง€์ •ํ•œ ์œ„์น˜์˜ ์›์†Œ
    //  * @throws IndexOutOfBoundsException index๊ฐ€ ๋ฒ”์œ„๋ฅผ ๋ฒ—์–ด๋‚˜๋ฉด,
    //  * ์ฆ‰, ({@code index < 0 || index >= this.size()})์ด๋ฉด ๋ฐœ์ƒํ•œ๋‹ค.
    //  */
    // E get(int index) {
    //     return null;
    // }

    // ์ž๊ธฐ์‚ฌ์šฉ ํŒจํ„ด ๋“ฑ ๋‚ด๋ถ€ ๊ตฌํ˜„ ๋ฐฉ์‹์„ ๋ช…ํ™•ํžˆ ๋“œ๋Ÿฌ๋‚ด๊ธฐ ์œ„ํ•ด @implSpec ์‚ฌ์šฉ (335์ชฝ)
    /**
     * Returns true if this collection is empty.
     *
     * @implSpec This implementation returns {@code this.size() == 0}.
     *
     * @return true if this collection is empty
     */
    public boolean isEmpty() {
        return false;
    }
    // ํ•œ๊ธ€ ๋ฒ„์ „
    // /**
    //  * ์ด ์ปฌ๋ ‰์…˜์ด ๋น„์—ˆ๋‹ค๋ฉด true๋ฅผ ๋ฐ˜ํ™˜ํ•œ๋‹ค.
    //  *
    //  * @implSpec ์ด ๊ตฌํ˜„์€ {@code this.size() == 0}์˜ ๊ฒฐ๊ณผ๋ฅผ ๋ฐ˜ํ™˜ํ•œ๋‹ค.
    //  *
    //  * @return ์ด ์ปฌ๋ ‰์…˜์ด ๋น„์—ˆ๋‹ค๋ฉด true, ๊ทธ๋ ‡์ง€ ์•Š์œผ๋ฉด false
    //  */
    // public boolean isEmpty() {
    //     return false;
    // }

    
    // ๋ฌธ์„œํ™” ์ฃผ์„์— HTML์ด๋‚˜ ์ž๋ฐ”๋… ๋ฉ”ํƒ€๋ฌธ์ž๋ฅผ ํฌํ•จ์‹œํ‚ค๊ธฐ ์œ„ํ•ด @literal ํƒœ๊ทธ ์‚ฌ์šฉ (336์ชฝ)
    /**
     * A geometric series converges if {@literal |r| < 1}.
     */
    public void fragment() {
    }
    // ํ•œ๊ธ€ ๋ฒ„์ „ 
    // /**
    //  * {@literal |r| < 1}์ด๋ฉด ๊ธฐํ•˜ ์ˆ˜์—ด์ด ์ˆ˜๋ ดํ•œ๋‹ค.
    //  */
    // public void fragment() {
    // }

    // ๋ฌธ์„œํ™” ์ฃผ์„ ์ฒซ '๋ฌธ์žฅ'์— ๋งˆ์นจํ‘œ๊ฐ€ ์žˆ์„ ๋•Œ ์š”์•ฝ ์„ค๋ช… ์ฒ˜๋ฆฌ (337์ชฝ)
    /**
     * A suspect, such as Colonel Mustard or {@literal Mrs. Peacock}.
     */
    public enum Suspect {
        MISS_SCARLETT, PROFESSOR_PLUM, MRS_PEACOCK, MR_GREEN, COLONEL_MUSTARD, MRS_WHITE
    }
    // ํ•œ๊ธ€ ๋ฒ„์ „
    // /**
    //  * ๋จธ์Šคํƒ€๋“œ ๋Œ€๋ น์ด๋‚˜ {@literal Mrs. ํ”ผ์ฝ•} ๊ฐ™์€ ์šฉ์˜์ž.
    //  */
    // public enum Suspect {
    //     MISS_SCARLETT, PROFESSOR_PLUM, MRS_PEACOCK, MR_GREEN, COLONEL_MUSTARD, MRS_WHITE
    // }

    // ์ž๋ฐ”๋… ๋ฌธ์„œ์— ์ƒ‰์ธ ์ถ”๊ฐ€ํ•˜๊ธฐ - ์ž๋ฐ” 9๋ถ€ํ„ฐ ์ง€์› 
    /**
     * This method complies with the {@index IEEE 754} standard.
     */
    public void fragment2() {
    }
    // ํ•œ๊ธ€ ๋ฒ„์ „ 
    // /**
    //  * ์ด ๋ฉ”์„œ๋“œ๋Š” {@index IEEE 754} ํ‘œ์ค€์„ ์ค€์ˆ˜ํ•œ๋‹ค.
    //  */
    // public void fragment2() {
    // }

    
    // ์—ด๊ฑฐ ์ƒ์ˆ˜ ๋ฌธ์„œํ™” 
    /**
     * An instrument section of a symphony orchestra.
     */
    public enum OrchestraSection {
        /** Woodwinds, such as flute, clarinet, and oboe. */
        WOODWIND,

        /** Brass instruments, such as french horn and trumpet. */
        BRASS,

        /** Percussion instruments, such as timpani and cymbals. */
        PERCUSSION,

        /** Stringed instruments, such as violin and cello. */
        STRING;
    }
    // ํ•œ๊ธ€ ๋ฒ„์ „
    // /**
    //  * ์‹ฌํฌ๋‹ˆ ์˜ค์ผ€์ŠคํŠธ๋ผ์˜ ์•…๊ธฐ ์„ธ์…˜.
    //  */
    // public enum OrchestraSection {
    //     /** ํ”Œ๋ฃจํŠธ, ํด๋ผ๋ฆฌ๋„ท, ์˜ค๋ณด ๊ฐ™์€ ๋ชฉ๊ด€์•…๊ธฐ. */
    //     WOODWIND,
    // 
    //     /** ํ”„๋ Œ์น˜ ํ˜ธ๋ฅธ, ํŠธ๋ŸผํŽซ ๊ฐ™์€ ๊ธˆ๊ด€์•…๊ธฐ. */
    //     BRASS,
    // 
    //     /** ํƒํŒŒ๋‹ˆ, ์‹ฌ๋ฒŒ์ฆˆ ๊ฐ™์€ ํƒ€์•…๊ธฐ. */
    //     PERCUSSION,
    // 
    //     /** ๋ฐ”์ด์˜ฌ๋ฆฐ, ์ฒผ๋กœ ๊ฐ™์€ ํ˜„์•…๊ธฐ. */
    //     STRING;
    // }

    
    // ์• ๋„ˆํ…Œ์ด์…˜ ํƒ€์ž… ๋ฌธ์„œํ™”
    /**
     * Indicates that the annotated method is a test method that
     * must throw the designated exception to pass.
     */
    @Retention(RetentionPolicy.RUNTIME)
    @Target(ElementType.METHOD)
    public @interface ExceptionTest {
        /**
         * The exception that the annotated test method must throw
         * in order to pass. (The test is permitted to throw any
         * subtype of the type described by this class object.)
         */
        Class<? extends Throwable> value();
    }
    // ํ•œ๊ธ€ ๋ฒ„์ „
    // /**
    //  * ์ด ์• ๋„ˆํ…Œ์ด์…˜์ด ๋‹ฌ๋ฆฐ ๋ฉ”์„œ๋“œ๋Š” ๋ช…์‹œํ•œ ์˜ˆ์™ธ๋ฅผ ๋˜์ ธ์•ผ๋งŒ ์„ฑ๊ณตํ•˜๋Š”
    //  * ํ…Œ์ŠคํŠธ ๋ฉ”์„œ๋“œ์ž„์„ ๋‚˜ํƒ€๋‚ธ๋‹ค.
    //  */
    // @Retention(RetentionPolicy.RUNTIME)
    // @Target(ElementType.METHOD)
    // public @interface ExceptionTest {
    //     /**
    //      * ์ด ์• ๋„ˆํ…Œ์ด์…˜์„ ๋‹จ ํ…Œ์ŠคํŠธ ๋ฉ”์„œ๋“œ๊ฐ€ ์„ฑ๊ณตํ•˜๋ ค๋ฉด ๋˜์ ธ์•ผ ํ•˜๋Š” ์˜ˆ์™ธ.
    //      * (์ด ํด๋ž˜์Šค์˜ ํ•˜์œ„ ํƒ€์ž… ์˜ˆ์™ธ๋Š” ๋ชจ๋‘ ํ—ˆ์šฉ๋œ๋‹ค.)
    //      */
    //     Class<? extends Throwable> value();
    // }
}
profile
https://dev-peter.online/

2๊ฐœ์˜ ๋Œ“๊ธ€

comment-user-thumbnail
2022๋…„ 3์›” 23์ผ

๋„ˆ๋ฌด ์œ ์ตํ•ด์š” ^^

1๊ฐœ์˜ ๋‹ต๊ธ€