Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
39 changes: 39 additions & 0 deletions 5장/최호.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
# Part 5: 형식 맞추기

### 인상 깊었던 내용

- 형식을 깔끔하게 맞추는 것 자체가 프로그래머의 책임이다.

- 신문 기사처럼 작성하라
→ 소스파일 상단은 고차원 개념, 아래로 갈수록 세부사항. 독자의 이해 흐름을 고려.

- 빈 행은 '새로운 개념'이라는 시각적 단서
→ 독자의 시선을 끌며 구조적인 단절을 유도함.

- 서로 관련된 코드 행은 세로로 가깝게 배치
→ 읽는 흐름 그대로 연관성을 인지 가능.

- 변수는 사용하는 위치에 가까이 선언
→ 예측 가능한 범위에서 관리 가능.

- 인스턴스 변수는 클래스 가장 위에 선언
→ 클래스 전반에 영향을 주는 변수는 눈에 띄게.

- 종속 함수는 서로 가깝게 배치하고, 호출하는 쪽이 먼저
→ 읽는 사람이 순차적으로 흐름을 이해할 수 있도록.

- 개념적 유사성은 물리적 거리로 표현
→ 밀접한 로직은 함께 두기.

- 공백도 의미가 있다

- a = b + c 와 같이 연산자는 공백을 주어 강조

- 함수명과 괄호는 공백 없이 붙여서 밀접함 표현

💬 느낀 점
- 팀 프로젝트에서 코딩 규칙을 미리 정하는 것의 중요성을 다시금 느꼈다.
→ 초반에 “일단 하자”는 말로 넘겼던 작은 차이들이, 나중에는 정리할 수 없을 정도로 번진다.
Comment on lines +35 to +36
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

인정합니다


- 공백 하나, 줄 간격 하나도 응집도와 결합도를 시각적으로 표현할 수 있다는 점이 인상 깊었다.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

저도 공백 하나 줄바꿈 한 줄의 힘을 느꼈습니다!

앞으로 코드를 "보여주는 글"처럼 쓴다는 마음가짐을 가져야겠다고 느꼈다.
22 changes: 22 additions & 0 deletions 6장/최호.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
# Part 6: 객체와 자료구조

### 인상 깊었던 내용

- 변수를 비공개로 정의하는 이유가 있다. 하지만 조회 함수와 설정 함수를 당현하게 공개해 비공개 변수를 외부에 노출할까?
- 객체는 추상화 뒤로 자료를 숨긴 채 자료를 다루는 함수만 공개한다.
- 절차적인 코드는 기존 자료 구조를 변경하지 않으면서 새 함수를 추가하기 쉽다. 반면, 객체 지향 코드는 기존 함수를 변경하지 않으면서 새 클래스를 추가하기 쉽다.
- 객체 지향 코드에서 어려운 변경은 저차적인 코드에서 쉬우며, 절차적인 코드에서 어려운 변경은 객체 지향 코드에서 쉽다.
- `final String outputDir = ctxt.getOptinos().getScratchDir().getAbsolutePath();` 이런 코드를 기차 충돌이라고 한다. 위 코드는 다음과 같이 나누는 편이 좋다.
```java
Options opts = ctxt.getOptions();
File scratchDir = opts.getScratchDir();
final String outputDir = scratchDir.getAbsolutePath();
```
- 객체라면 내부 구조를 숨겨야 하므로 확실히 디미터 법칙을 위반한다. 반면, 자료구조라면 당연히 내부구조를 노출하므로 디미터 법칙이 적용되지 않는다. -> `final String outputDir = ctxt.optinos.scratchDir.absolutePath;`
- 시스템을 구현할 때, 새로운 자료 타입을 추가하는 유연성이 필요하면 객체가 더 적합하다. 다른 경우로 새로운 동작을 추가하는 유연성이 필요하면 자료 구조와 절차적인 코드가 적합하다.


💬 느낀 점
- 사실 프론트는 절차 지향 코딩을 하기때문에 이번 장 내용이 잘 이해되지 않았다.
- 백엔드는 새로운 자료 타입을 추가하는 일이 많기 때문에 객체 지향 코딩을 한다고 이해했고, 프론트는 동작 중심이기 때문에 자료구조와 절차적인 코드가 적합하다고 이해했다.
Comment on lines +20 to +21
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

저도 좀 헷갈립니다..이 부분 다음에 한 번 같이 논의해 봐도 좋을 것 같아요.

- 하지만 결국 중요한건 개발자의 판단 능력이 아닐까란 생각이 들었다.
95 changes: 95 additions & 0 deletions 7장/최호.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,95 @@
# Part 7: 오류 처리

### 인상 깊었던 내용

- 깨끗한 코드와 오류 처리는 확실히 연관성이 있다.
```ts
// Bad
const res = await fetch("/api/user");
if (!res) return;
if (!res.ok) return;
const data = await res.json();

// Good
try {
const res = await fetch("/api/user");
if (!res.ok) throw new Error("사용자 정보 로딩 실패");
const data = await res.json();
return data;
} catch (e) {
console.error(e);
showToast("유저 정보를 불러올 수 없습니다.");
}
```
- 흩어진 오류 처리 코드 때문에 실제 코드가 하는 일을 파악하기가 거의 불가능하다.
```ts
// Bad
if (!user) return;
if (!user.profile) return;
if (!user.profile.name) return;
render(user.profile.name);

// Good
try {
const name = user?.profile?.name;
if (!name) throw new Error("이름 정보 없음");
render(name);
} catch {
showToast("유저 정보가 올바르지 않습니다.");
}
```
- 오류 코드보다 예외를 사용해라
```ts
// Bad
function findItem(id) {
return items.find(i => i.id === id) || null;
}

// Good
function findItem(id) {
const item = items.find(i => i.id === id);
if (!item) throw new Error(\`아이템을 찾을 수 없음: \${id}\`);
return item;
}
```
- 오류 코드를 사용하면 호출자 코드가 호출된 즉시 오류를 확인해야하기 때문이다.
- Try-Catch-Finally문부터 작성하라
- 미확인 예외를 사용해라.
- 확인된 예외는 OCP를 위반한다.
- 때로는 확인된 예외도 유용하다. 아주 중요한 라이브러리를 작성한다면 모든 예외를 잡아야 한다. 하지만 일반적인 앱은 의존성이라는 비용이 이익보다 크다.
- 오류 메시지에 정보를 담아 예외와 함께 던져라.
```ts
function getUserName(user: any) {
if (!user?.name) {
throw new Error("user 객체에 name 속성이 없습니다.");
}
return user.name;
}
```
- 정상 흐름을 정의하라
```ts
// Bad
try {
if (!form.email) throw new Error("이메일 누락");
} catch {
showToast("이메일을 입력해주세요.");
}

// Good
if (!form.email) {
showToast("이메일을 입력해주세요.");
return;
}
```


### 💬 느낀 점
- 이번 장은 백엔드 중심의 객체 지향적 예외 처리 관점이 강했지만, 프론트엔드에서도 에러 처리 설계가 매우 중요하다는 것을 느꼈다.

- 프론트엔드는 UI 흐름이 많아 절차적 코드가 주로 사용되지만, 예외 상황에 대한 처리는 여전히 핵심적인 개발 역량이다.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

절차지향 프로그래밍이라면 사용자가 할 행동을 예측하여, 또는 그대로 따르게 하는 방향으로 프로그래밍을 하는 것일까요?
그렇다면 객체지향보다는 예외 상황이 덜 할 수는 있으나, 사용자가 예기치 못 한 동작을 할 수도 있으니 결국 예외처리는 프/백 둘 다 중요한 것 같습니다!


- 사용자에게 보여줄 메시지와 개발자가 확인할 로그를 분리하는 처리 방식이 특히 중요하다고 느꼈다.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

맞습니다. 사용자에게 적절한 메세지를 보여주는 것이 UX/UI에서 정말 중요하다고 느낍니다!


- try-catch 구문은 남용하기보다는 실패 가능성이 높은 최소 범위에만 쓰는 것이 가독성과 유지보수에 유리하다는 점을 다시금 되새겼다.

- 중요한 것은 결국 개발자가 언제 예외를 사용하고, 언제 정상 흐름으로 처리할지를 판단할 수 있는 능력이라는 생각이 들었다.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

최대한 고객의 입장에서 많이 고민해 보고, 여러 상황을 테스트 해 보며 처리하는 것이 최선인 듯 해요.