๋งํด ํ์ธ๋ฌ(Martin Fowler)์ ์ ์ "๋ฆฌํฉํ ๋ง 2ํ: ์ฝ๋ ๊ตฌ์กฐ๋ฅผ ์ฒด๊ณ์ ์ผ๋ก ๊ฐ์ ํ์ฌ ํจ์จ์ ์ธ ๋ฆฌํฉํฐ๋ง ๊ตฌํํ๊ธฐ"๋ฅผ ์ฝ๊ณ ๊ณต๋ถํ ๋ด์ฉ์ ๊ธฐ๋กํ์ต๋๋ค. (์ฑ ์ ๋์จ javascript ์์๋ฅผ typescript๋ก ๋ณํํ์ต๋๋ค.)
Chapter 01 ๋ฆฌํฉํฐ๋ง: ์ฒซ ๋ฒ์งธ ์์
- ํ๋ก๊ทธ๋จ์ด ์๋ก์ด ๊ธฐ๋ฅ์ ์ถ๊ฐํ๊ธฐ์ ํธํ ๊ตฌ์กฐ๊ฐ ์๋๋ผ๋ฉด, ๋จผ์ ๊ธฐ๋ฅ์ ์ถ๊ฐํ๊ธฐ ์ฌ์ด ํํ๋ก ๋ฆฌํฉํฐ๋งํ๊ณ ๋์ ์ํ๋ ๊ธฐ๋ฅ์ ์ถ๊ฐํ๋ค.
- ๋ฆฌํฉํฐ๋ง์ ์ฒซ๋จ๊ณ
: ๋ฆฌํฉํฐ๋งํ๊ธฐ ์ ์ ์ ๋๋ก ๋ ํ ์คํธ๋ถํฐ ๋ง๋ จํ๋ค. ํ ์คํธ๋ ๋ฐ๋์ ์๊ฐ์ง๋จํ๋๋ก ๋ง๋ ๋ค. - ๋ฆฌํฉํฐ๋ง์ ํ๋ก๊ทธ๋จ ์์ ์ ์์ ๋จ๊ณ๋ก ๋๋ ์งํํ๋ค. ๊ทธ๋์ผ ์ค๊ฐ์ ์ค์ํ๋๋ผ๋ ๋ฒ๊ทธ๋ฅผ ์ฝ๊ฒ ์ฐพ์ ์ ์๋ค.
- ๊ธด ํจ์๋ฅผ ๋ฆฌํฉํฐ๋งํ ๋๋ ๋จผ์ ์ ์ฒด ๋์์ ๊ฐ๊ฐ์ ๋ถ๋ถ์ผ๋ก ๋๋ ์ ์๋ ์ง์ ์ ์ฐพ๋๋ค.
- ๋ณ๋ ํจ์๋ก ๋นผ๋์ ๋ ์ ํจ๋ฒ์๋ฅผ ๋ฒ์ด๋๋ ๋ณ์, ์ฆ ์ ํจ์์์๋ ๊ณง๋ฐ๋ก ์ฌ์ฉํ ์ ์๋ ๋ณ์๊ฐ ์๋์ง ํ์ธํ๋ค.
- ์๋ค๋ฉด, ์ด ๋ณ์๋ฅผ ์ด๊ธฐํํ๋ ์ฝ๋์ ํจ๊ป ํด๋น ๊ฐ์ ๋ฐํํ๋๋ก ์์ฑํ๋ค.
- ์์ ํ๊ณ ๋ ํ ๊ณง๋ฐ๋ก ์ปดํ์ผํ๊ณ ํ ์คํธํด์ ์ค์ํ๊ฒ ์๋์ง ํ์ธํ๋ค
- ์์ ๋ณ์๋ค์ ๋ก์ปฌ ๋ฒ์์ ์กด์ฌํ๋ ์ด๋ฆ์ด ๋์ด๋์ ์ถ์ถ ์์ ์ด ๋ณต์กํด ์ง๊ธฐ ๋๋ฌธ์ ์ต๋ํ ์ ๊ฑฐ ํ๋ค.
- ์ง์ญ ๋ณ์๋ฅผ ์ ๊ฑฐํด์ ์ป๋ ๊ฐ์ฅ ํฐ ์ฅ์ ์ ์ถ์ถ ์์ ์ด ํจ์ฌ ์ฌ์์ง๋ค๋ ๊ฒ์ด๋ค.
- ์ฝ๋๊ฐ ๋ณต์กํ ์๋ก, ๋จ๊ณ๋ฅผ ์๊ฒ ๋๋์ด ์์ ํ๊ณ ์ปค๋ฐ์ ์์ฃผ ํ์.
[์์ฝ]
- ๋ฐ๋ณต๋ฌธ ์ชผ๊ฐ๊ธฐ : ๋ณ์ ๊ฐ์ ๋์ ์ํค๋ ๋ถ๋ถ์ ๋ถ๋ฆฌํ๋ค.
- ๋ฌธ์ฅ ์ฌ๋ผ์ด๋ ํ๊ธฐ : ๋ณ์ ์ด๊ธฐํ ๋ฌธ์ฅ์ ๋ณ์ ๊ฐ ๋์ ์ฝ๋ ๋ฐ๋ก ์์ผ๋ก ์ฎ๊ธด๋ค.
- ํจ์ ์ถ์ถํ๊ธฐ : ์ ๋ฆฝ ํฌ์ธํธ ๊ณ์ฐ ๋ถ๋ถ์ ๋ณ๋ ํจ์๋ก ์ถ์ถํ๋ค.
- ๋ณ์ ์ธ๋ผ์ธํ๊ธฐ : ์ถ์ถํ ํจ์๋ฅผ ์ด์ฉํด ๋ณ์๋ฅผ ์ ๊ฑฐํ๋ค.
[๋ฆฌํฉํ ๋ง ์ ]
import { I_PLAYS } from "../../interfaces/play";
import { I_INVOICES } from "../../interfaces/invoice";
function Statement(invoice: I_INVOICES, plays: I_PLAYS): string {
let totalAmount: number = 0;
let volumeCredits: number = 0;
let result: string = `์ฒญ๊ตฌ ๋ด์ญ (๊ณ ๊ฐ๋ช
: ${invoice.customer})\n`;
const format = new Intl.NumberFormat("es-US", {
style: "currency",
currency: "USD",
minimumFractionDigits: 2,
}).format;
for (let perf of invoice.performances) {
const play = plays[perf.playID];
let thisAmount = 0;
switch (play.type) {
case "tragedy": // ๋น๊ทน
thisAmount = 40000;
if (perf.audience > 30) {
thisAmount += 1000 * (perf.audience - 30);
}
break;
case "comedy": // ํฌ๊ทน
thisAmount = 30000;
if (perf.audience > 20) {
thisAmount += 10000 + 500 * (perf.audience - 20);
}
thisAmount += 300 * perf.audience;
break;
default:
throw new Error(`์ ์ ์๋ ์ฅ๋ฅด : ${play.type}`);
}
//ํฌ์ธํธ๋ฅผ ์ ๋ฆฝํ๋ค.
volumeCredits += Math.max(perf.audience - 30, 0);
if (play.type === "comedy") volumeCredits += Math.floor(perf.audience / 5);
//์ฒญ๊ตฌ ๋ด์ญ์ ์ถ๋ ฅํ๋ค.
result += ` ${play.name} : ${format(thisAmount / 100)} (${
perf.audience
}์)\n`;
totalAmount += thisAmount;
}
result += `์ด์ก : ${format(totalAmount / 100)}\n`;
result += `์ ๋ฆฝ ํฌ์ธํธ : ${volumeCredits}์ \n`;
return result;
}
export { Statement };
[๋ฆฌํฉํ ๋ง ํ]
import { I_PLAY, I_PLAYS } from "../../interfaces/play";
import { I_INVOICE_PLAY, I_INVOICES } from "../../interfaces/invoice";
function Statement(invoice: I_INVOICES, plays: I_PLAYS): string {
function AmountFor(perf: I_INVOICE_PLAY, play: I_PLAY): number {
// ๊ฐ์ด ๋ฐ๋์ง ์๋ ๋ณ์๋ ๋งค๊ฐ๋ณ์๋ก ์ ๋ฌ
let thisAmount = 0; // ๋ณ์๋ฅผ ์ด๊ธฐํ ํ๋ ์ฝ๋
switch (play.type) {
case "tragedy": // ๋น๊ทน
thisAmount = 40000;
if (perf.audience > 30) {
thisAmount += 1000 * (perf.audience - 30);
}
break;
case "comedy": // ํฌ๊ทน
thisAmount = 30000;
if (perf.audience > 20) {
thisAmount += 10000 + 500 * (perf.audience - 20);
}
thisAmount += 300 * perf.audience;
break;
default:
throw new Error(`์ ์ ์๋ ์ฅ๋ฅด : ${play.type}`);
}
return thisAmount; // ํจ์ ์์์ ๊ฐ์ด ๋ฐ๋๋ ๋ณ์ ๋ฐํ
}
let totalAmount: number = 0;
let volumeCredits: number = 0;
let result: string = `์ฒญ๊ตฌ ๋ด์ญ (๊ณ ๊ฐ๋ช
: ${invoice.customer})\n`;
const format = new Intl.NumberFormat("es-US", {
style: "currency",
currency: "USD",
minimumFractionDigits: 2,
}).format;
for (let perf of invoice.performances) {
const play: I_PLAY = plays[perf.playID];
let thisAmount: number = AmountFor(perf, play);
volumeCredits += Math.max(perf.audience - 30, 0);
if (play.type === "comedy") volumeCredits += Math.floor(perf.audience / 5);
result += ` ${play.name} : ${format(thisAmount / 100)} (${
perf.audience
}์)\n`;
totalAmount += thisAmount;
}
result += `์ด์ก : ${format(totalAmount / 100)}\n`;
result += `์ ๋ฆฝ ํฌ์ธํธ : ${volumeCredits}์ \n`;
return result;
}
export { Statement };
LIST
'๐ > ์์ ๐' ์นดํ ๊ณ ๋ฆฌ์ ๋ค๋ฅธ ๊ธ
[Refactoring] Chapter 03. Bad Smells in Code (์ฝ๋์์ ๋๋ ์ ์ทจ) (1) | 2024.02.02 |
---|---|
[Refactoring] Chapter 02. Principles in Refactoring (๋ฆฌํฉํฐ๋ง ์์น) (1) | 2024.01.25 |