Repository navigation
Kangdaeho Chapter 02. 문자열 계산기 구현 - #2
kangdaeho99 wants to merge 34 commits into
Conversation
개발 환경 설정 및 요구사항 문서 추가.
This reverts commit 326ca54.
…/feature/clean-ignore github에 올라간 iml 제거 및 ignore에서 프로젝트명 관계없이 iml 제외되도록 변경
|
[제안] 시작하기 전에 내가 구현해야할 기능목록에 대해서 먼저 생각해보고 적는 습관을 들여보는게 어떨까 싶어요 |
| } | ||
|
|
||
| dependencies { | ||
| implementation 'junit:junit:4.13.1' |
There was a problem hiding this comment.
There was a problem hiding this comment.
넵 JUnit 5를 사용해보면서, JUnit과는 차이점이 있네요
먼저 의존성은 아래처럼 가져왔어요~!
dependencies {
implementation 'org.junit.jupiter:junit-jupiter:5.8.1'
testImplementation 'org.junit.jupiter:junit-jupiter-api:5.8.1'
testRuntimeOnly 'org.junit.jupiter:junit-jupiter-engine:5.8.1'
}
또 JUnit5의 테스트 메서드를 사용하려면, Jupiter API를 Import해서 사용합니다
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
위에 Jupiter API를 Import해서 사용해요.
또, 사용하면서 느꼈던 차이점은 JUnit4에서 @before가 JUnit5에서는 @beforeeach 로 바뀌었네요
There was a problem hiding this comment.
Junit5의 테스트 메서드 대신 assertj 로 테스트 툴을 바꿔봤네요
먼저 의존성은 아래처럼 가져왔어요~!
testImplementation 'org.assertj:assertj-core:3.21.0'
assertJ의 테스트메서드가 junit5보다 직관적이네요
There was a problem hiding this comment.
[질문] Calculator의 삭제는 깜빡하신거죠?
| int add(String text){ | ||
| //빈 문자열 또는 null값을 입력할 경우 0을 반환한다. | ||
| if(text == null || text.isEmpty()){ | ||
| return 0; |
There was a problem hiding this comment.
[질문] null이거나 빈 문자열일 경우 0을 반환한 이유가 있을까요?
2.3.1 요구사항에는 빈 문자열 또는 null 에 대해서 어떻게 처리하라고 나와있지 않았어요.
2.3.2 힌트에는 빈 문자열과 null에 대해서 0을 반환해야 한다 라는 조건이 나와있죠.
(실무를 접해보지 않았지만,,,박재성님 말로는) 실무에서는 요구조건 사항을 디테일 하게 주지 않아요.
만약에 빈 문자열, null일 경우 0을 반환하면 안되는 상황이 있을까요?
그렇다면, 0을 반환하지 않고 어떤 방식을 사용해야할까요?
위 내용은 "좋은 코드 나쁜 코드" 에서도 다루는 내용이예요 아마 클린코드에서도 다룰 것 같네요
There was a problem hiding this comment.
[질문] null이거나 빈 문자열일 경우 0을 반환한 이유가 있을까요?
[답변 1.] 힌트까지 보고 개발을 진행했는데, 힌트에 나온 내용을 그대로 사용했어요
[질문] 만약에 빈 문자열, null일 경우 0을 반환하면 안되는 상황이 있을까요?
[답변 2.]. 만약, 이 프로그램이 실제로 사용자의 입력에 따라 어떤 점수를 계산하는데, 사용자가 아무 입력도 하지 않았는데 0을 반환되는 상황을 생각해봤어요.
해당 상황에서 "0을 반환하면 안되는 상황이 있을까?"에 대해서 질문을 받았을떄, 만약 계산기에 add 외에도 divide 가 추가되었을떄 divide by zero ArithmeticException 이 발생할 수 있을 것 같아요
[질문] 그렇다면, 0을 반환하지 않고 어떤 방식을 사용해야할까요?
[답변 3.]throw new IllegalArgumentException("Input cannot be null or empty"); 와 같이 Exception을 발생시키는 방안이 있을 것 같아요!
| // 구분자로 사용한다. 예를 들어 "//;\n1;2;3"과 같이 입력할 경우 커스텀 구분자는 세미콜론(;) 이며, 결과값은 6이 반환되어야 한다. | ||
| //문자열 계산기에 음수를 전달하는 경우 RuntimeException으로 예외처리해야 한다. | ||
| if(text.startsWith("//")){ | ||
| Matcher m = Pattern.compile("//(.)\n(.*)").matcher(text); |
There was a problem hiding this comment.
[질문] "//" 과 "//(.)\n(.*)"는 하드 코딩이네요.
하드 코딩을 하지 말아야하는 이유에 대해서 공부해볼만 할 것 같아요.
There was a problem hiding this comment.
[답변] 가장 큰 이유는 요구사항 변경(새로운 기능 추가나 수정)시에 유지보수의 어려움이네요.
예시로 만약, 요구사항이 변경되어서 "//(.)\n(.)" 가 "&&(.)&n(.)" 로 변경된다면 이 //(.)\n(.*)" 를 사용하던 모든 클래스들을 직접 변경시켜줘야한다는 점이 문제인 것 같아요.
| // 구분자로 사용한다. 예를 들어 "//;\n1;2;3"과 같이 입력할 경우 커스텀 구분자는 세미콜론(;) 이며, 결과값은 6이 반환되어야 한다. | ||
| //문자열 계산기에 음수를 전달하는 경우 RuntimeException으로 예외처리해야 한다. | ||
| if(text.startsWith("//")){ | ||
| Matcher m = Pattern.compile("//(.)\n(.*)").matcher(text); |
There was a problem hiding this comment.
[제안] Macher 타입의 변수를 m 이라고 적어놨네요. 변수명을 누가봐도 알기 쉽게 지어보는 것이 어떨까요?
There was a problem hiding this comment.
[답변] 넵, customDelimiterMatcher 로 수정하면 커스텀구분자 Matcher 변수명으로 하면 이해하기 쉬울 것 같아요! 더 좋은 네이밍 있으면 공유 부탁드립니다!!
| import java.util.regex.Matcher; | ||
| import java.util.regex.Pattern; | ||
|
|
||
| public class StringCalculator { |
There was a problem hiding this comment.
[질문] 2.3.3 추가 요구사항에 "메서드가 한 가지 책임만 가지도록 구현한다"
라고 나와있어요
한가지 책임이 무엇을 의미하고, 어떻게 한가지 책임만 가지도록 할 수 있을까요?
한번에 너무 많은 것을 리팩토링 하려고 하지말고, 위의 내용을 생각해보면서 지금 코드에서 어떻게 하면 책임을 줄일 수 있을까 생각해보는 것이 도움이 될 것 같아요.
"객체지향 생활 체조" 에 대해서 검색해보는 것도 추천드립니다.
There was a problem hiding this comment.
[답변] 한가지 책임이란, 하나의 메소드가 하나의 목적을 위해 존재하는거라고 생각했어요.
우선 각 메소드 당 한가지 책임만 가지도록 리팩토링해봤습니다!
validateInput(String text)의 책임: 입력 문자열의 유효성을 검사합니다.
sumWithCustomDelimiter(String text)의 책임: 커스텀 구분자를 사용하는 문자열을 처리합니다.
sumWithDefaultDelimiter(String text)의 책임: 기본 구분자를 사용하는 문자열을 처리합니다.
객체지향 생활체조 9가지 원칙에 대해서 찾아보았는데, 상당히 인상적이네요. 우선은 각 메소드 당 한가지 책임만 가지는걸 중점으로 해서 리팩토링해봤습니다!
No description provided.