필독 개발자 온보딩 가이드을 읽고 정리하는 글이며, 혹시 문제가 되면 삭제하겠습니다.
학습을 위한 가르침이라는 책에서
능숙함
을 4가지 단계로 나누어 의미 했다.
1. 무의식적 능력 부족
2. 의식적 능력 부족
3. 의식적 능숙
4. 무의식적 능숙모든 엔지니어는 의식적이든 무의식적이든 능력 부족 단계에서 시작하며, 목표는 최대한 빨리 의식적 능숙 단계로 접어드는 것이 좋다.
또한 이 장에서 자기주도 학습이라는 습관 방법과 균형 유지, 가면 증후군, 더닝 크루거 효과에 대해서도 다룬다.
스스로에 대한 불신이나 과신에 빠지지 않도록 주의하며 자기주도 학습을 계속하고 효율적인 질문을 하다 보면 의식적 능숙함을 빠르게 갖출 수 있을 것이다.
이 초반 과정은 지루할 수도 있고 다른 사람은 바쁜데 마치 자신만 한가한 것 같은 느낌도 들 것이다.
하지만 걱정마라. 적응할 시간이 필요하다는 사실은 모든 사람이 알고 있을 것이다.
코드를 처음 배포할 때 어딘가 문제가 생기지 않을 두려울 수 있지만 팀장들도 녹록치 않아서 결코 심각한 피해를 입힐 만한 상황을 만들지 않는다.
(디만 대안이 없는 경우 신규 입사자가 위험 부담 높은 작업에 투입될 때도 있다.)
어떤 메소드가 호출이 된 것은 알겠는데 도대체 어떤 경로로 그 메소드가 호출됐는지 알아내지 못하는 경우가 있다. 이럴 때는
예외
를 던지거나스택 트레이스
를 출력해보거나 아니면디버거
를 붙여 호출 경로를 살펴보는 등의 시도
일단 출처
https://jaehoney.tistory.com/51
https://okky.kr/articles/338405
public class StackTraceTest
{
public static void main(String[] args)
{
one();
}
public static void one()
{
two();
}
public static void two()
{
three();
}
public static void three()
{
Integer.parseInt("abcde");
}
}
1. 스택트레이스는 에러가 발생된 시점부터 프로그램이 시작된 시점까지 거슬러 올라가면서 출력되기 때문에 먼저 실행된 메서드가 가장 아래
2. 나도 보려고 노력하지만 겁먹기 마련이다. 대부분 처음 시작하는 분들이 그렇더라
3. 하지만 에러의 진정한 원인은 가장 아래쪽(초기)에 있는 Caused by:
로 시작되는 줄부터 아래로 세줄이면 충분
Caused by: java.lang.NullPointerException
at com.mycompany.service.impl.PortalManagerImpl.deleteMenuItem(PortalManagerImpl.java:603)
at com.mycompany.service.impl.PortalManagerImpl.deletePortal(PortalManagerImpl.java:358)
위의 내용은 com.mycompany.service.impl.PortalManagerImpl' 클래스의 deletePortal
메소드 358라인에서 같은 클래스의 deleteMenuItem
메소드를 호출했는데 해당 메소드 603번 째 줄에서 널포인터 예외가 발생했다라고 해석
okky의 질문
okky의 답변
deleteMenuItem()
은 재귀 호출을 하는 메서드라서 혼동이 되신 것 같습니다. 스택트레이스의 인용하신 부분은 "603번 째 줄에서 deleteMenuItem()을 호출할 때"가 아니라 "호출된 deleteMenuItem() 메서드의 내부의 603번 째 줄"임
🐇 좀 더 자세히 설명하자면,
deleteMenuItem() 메서드 내부에서 getMenuItems(item.getPortal().getId(), item.getId()) 메서드를 호출하려고 합니다. 이때, item이 null인 경우 NullArgumentException이 발생하고 예외가 던져집니다.
PortalManagerImpl
클래스 소스
if (item == null) {
throw new NullArgumentException("item");
}
//중간 생략
List<PortalMenu> children = getMenuItems(item.getPortal().getId(), item.getId()); // 603번째 줄
for (PortalMenu child : children) {
deleteMenuItem(child);
}
children
이나 item.getId()
등에 널값이 들어간 것 같다고 답했다고 한다. 이론적으로 해당 라인에서 널값이 들어갈 수 있는 모든 경우의 수는,
- children
- item
- item.getPortal()
- item.getPortal().getId()
- item.getId()
널포인터 예외는 단순하게 변수에 널값이 들어가서 생기는 오류가 아니다.
널포인터 예외
는 명확하게 객체의 널레퍼런스에 대해 메소드 호출이나 필드 참조 등의 작업을 했을 때 발생하는 문제라는 것을 이해한다면 이런 문제는 곧바로 원인을 좁힐 수 있어야 한다.
즉, 1번의 경우처럼 단순히 변수에 널값을 할당하는 것만으로는 절대로 널포인터 예외가 날 수 없다. 그리고 만일 4 번 item.getPortal().getId()
이나 5번 item.getId()
이 널이라면 이는 널 레퍼런스에 대한 호출이 아니라 널값을 getMenuItems
라는 메소드의 인자로 넘기는 것 뿐이기 때문에 역시 널포인터 예외의 원인이 될 수 없다.
물론 getMenuItem
메소드 안에서 해당 인자에 대한 널체크 없이 값을 사용하다가 예외가 날 수도 있겠지만 이 경우엔 절대로 트레이스 상에 굵은 글자로 표시된 603번 째에서 예외를 뿌리지 않는다.
그렇다면 남은 가능성은 2번 'item'이 널이거나 3번 'item.getPortal()'이 널인 경우뿐인데, 'item' 변수는 위에서 널체크를 하기 때문에 603번 째 줄에서 절대로 널값을 가질 수 없다. 그렇기 때문에 답은 3번이 되는 것
스택 트레이스 를 읽는 법을 찾다가 알게 된 것인데... 둘은 완전히 다르다는 것
Visual Studio는 IDE(통합 개발 환경)이며 Visual Studio Code는 Sublime Text 및 Atom과 같은 리치 텍스트 편집기로
도구 간의 차이점은 IDE와 텍스트 편집기 그 이상이라고 한다.
IDE는 코드 작성, 편집, 디버깅 및 실행을 위한 강력한 도구로 텍스트 편집기에서는 코드를 작성하고 편집할 수만 있다. 코드를 실행하거나 자동으로 실행되도록 플러그인을 다운로드하려면 텍스트 편집기에서 나가야 할 수도 있다고 함.. 깊게 공부 안하고 돌리기만 해서... 몰랐다.
IntelliJ IDEA를 열고 디버그할 프로젝트를 로드
1. 디버그하고 싶은 코드 파일을 엽니다.
2. 브레이크 포인트를 설정하려는 줄에 마우스 커서를 가져갑니다.
3. 해당 줄의 왼쪽 마진(라인 넘버 부분)을 클릭하면 브레이크 포인트가 설정됩니다. 또는, 해당 줄을 클릭한 후Ctrl + F8 (Windows/Linux)
또는Command + F8 (Mac)
을 누르면 컨텍스트 메뉴가 나타납니다. 이 메뉴에서Toggle Line Breakpoint
를 선택하면 브레이크 포인트가 설정됩니다.
4. 설정한 브레이크 포인트는빨간 동그라미
로 표시됩니다.
5. 디버그 모드로 실행하려면 해당 클래스 또는 메서드 내에서 마우스 우클릭하여 "Debug" 옵션을 선택하거나, 코드 에디터 상단의 "Run" 또는 "Debug" 버튼을 클릭합니다.
6. 프로그램이 브레이크 포인트에 도달하면 실행이 일시 정지됩니다. 이때 디버거 창에서 변수 값을 확인하거나 단계별로 코드를 실행해볼 수 있습니다.
읽을 자료는 무궁무진하다. 다만 이 자료들을 한 번에 모두 읽을 생각은 하지말자.
🍊 잠깐!! 트레이드 오프(trade-off)와 컨텍스트(context)란?
- 트레이드 오프 : 객체의 어느 한 부분을 품질을 높이거나 낮추는 데 다른 한쪽의 영향을 미치는 상황
EX. 개발의 시간 UP => 완성도 UP => 비용 UP 적절한 최적의 타협 필요- 컨텍스트 : 코드나 기능이 작동하는 환경, 어떤 특정 작업한 단위 수행한 필요한 기본정보, 준비사항, 그 경계의 지침
코드는 소설처럼 처음부터 끝까지 쭉 읽는 것이 아니다. IDE를 이용해 코드의 이곳저곳을 훑어보자. 주요 기능에 대해서는 코드의 흐름과 상태를 다이어그램으로 그려보자. 코드의 데이터 구조와 알고리즘을 파헤쳐보자. 예외 상황을 어떻게 처리하는지도 잘 살펴보자. 그러면서 팀의 코딩 스타일과 용어도 꼼꼼히 확인하자. 그래야 내부 의사소통이 원할해진다.
앞으로 해야 할 일은 티켓(ticket)이나 이슈(issue)로 관리한다.
1. 발표 영상을 찾아서 찾아보자
2. 때로는 밋업과 컨퍼런스를 참여하자.
3. 시니어 엔진니어의 체험하고 협업하자.
4. 개인 프로젝트 활동에서도 배움을 얻을 수 있다.
5. 제대로 질문하기
6. 스스로 문제를 해결해보자
아무런 단서도 찾지 못한다면 실험을 통해 스스로 해결해보자. 어디를 살펴봤는지 어떤 방법을 왜 시도했는지, 결과는 어땠는지 그리고 그로부터 배운 것은 무엇인지 모조리 기록하자.
단위 테스트
로 바뀌보자.7. 제한 시간을 정하자
문제를 스스로 해결하기 위한 기한을 정해두자.
8. 자신이 시도한 방법을 공유하자
9. 동료를 방해하지 말자
10. 비동기식 멀티캐스팅 의사소통을 시도하자.
11. 동기식 요청은 한 번만 보내자
⭕ 이것만은 지키자 | ❌ 이것만은 피하자 |
---|---|
코드를 이용해 자주 실험하자 | 아무 생각 없이 코드만 찍어내서는 안된다. |
설계문서와 다른 사람이 만든 코드를 읽자 | 위험과 실패를 두려워하지 말자 |
밋업, 온라인 커뮤니티, 관심 그룹, 멘토십 프로그램에 참여하자 | 너무 잦은 컨퍼런스 참석은 금물이다. |
멀티캐스트/비동기식으로 의사소통하자 | 질문하기를 두려워하지 말자. |
인터뷰나 면접 긴급대응 교대 업무를 따라 다녀보자 |
지금 글을 쓰고 있는 시점에는 3장까지 읽어봤는데 회사에 가서 처음 헤매는 사람이랑 공부하는 방향을 모르겠는 사람에게 좋은 것 같다. 특히 에러 났을 때 스택 트레이스를 보는 것 국비에서도 대부분 사람들이 이걸 보는 거 어려워 한다. 어 왜 안돼..? 왜..? 여기서 끝이고 무슨 이유인지 콘솔을 볼려고 하지 않는다 그건 나도 그런 것 같다.
거기서 보고 이유 뿐 아니라 위에서 설명한 것 처럼 nullpointException이 정확히 언제 나는 지 등을 알아두는 것 또한 중요하다 생각한다.