일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | |||||
3 | 4 | 5 | 6 | 7 | 8 | 9 |
10 | 11 | 12 | 13 | 14 | 15 | 16 |
17 | 18 | 19 | 20 | 21 | 22 | 23 |
24 | 25 | 26 | 27 | 28 | 29 | 30 |
- Kullback-Leibler Divergence
- 가상환경 제거
- object detection
- 프로그래머스 67258번
- augmentation 이후 이미지 확인
- 프로그래머스 42839번
- gradient descent optimization
- jupyter 명령어 모드 단축키
- jupyter 셀 추가 단축키
- 가상환경 확인
- 프로그래머스 72410번
- os 확인 명령어
- 백준 1325번
- 프로그래머스 67257번
- 원격서버 로컬 동기화
- 백준 3190번
- DeepLabv3+
- zip 압축해제 명령어
- pytorch 이미지 확인
- vscode sftp
- 프로그래머스 42883번
- 프로그래머스 42885번
- 카카오 보석 쇼핑
- YOLO detection
- MMdetection
- 프로그래머스 43164번
- Optimization algorithms
- 백준 효율적인 해킹
- 프로그래머스 보석 쇼핑
- 프로그래머스 67256번
- Today
- Total
소소한 블로그
[1주차 - Day3] unittest, mock.patch 본문
과제 skeleton code에서 unit test와 관련된 부분이 이해되지 않아 정리해봤습니다.
파이썬에서는 단위 테스트를 위해 unittest라는 단위 테스트 프레임워크를 지원하고 있습니다.
많은 활용이 가능하겠지만, 개인적으로는 사용자로부터 입력을 받아야 하는 모듈이라든지 출력문(print)의 형식을 확인해야할 때 유용한 프레임워크라고 느꼈습니다.
unittest에 대한 자세한 설명보다는 활용법을 통한 간단한 소개를 드리려 합니다.
예를 들어 아래와 같은 함수가 있습니다.
def main():
user_input = input("Input non-negative number : ")
if user_input.isdigit():
print("Valid")
else:
print("Invalid")
이 함수에 대해 단위 테스트를 하고 싶다고 가정하겠습니다.
가장 단순한 테스트는 main()을 호출하여 사용자가 하나씩 값을 입력해보며 출력문을 확인하는 방법이 있겠네요.
하지만 unittest를 활용하면 직접 값을 하나씩 입력하지 않아도 됩니다.
아래 코드는 unittest를 활용한 단위테스트 코드입니다.
import unittest
from mock import patch
from io import StringIO
class UnitTest(unittest.TestCase):
def test_main(self):
with patch('builtins.input', side_effect=["3", "1", "100", "0"]):
with patch('sys.stdout', new=StringIO()) as fakeOutput:
main()
console = fakeOutput.getvalue().strip().split("\n")
for print_value in console:
self.assertTrue("Valid" == print_value)
with patch('builtins.input', side_effect=["-1", "1.234", "abc"]):
with patch('sys.stdout', new=StringIO()) as fakeOutput:
main()
console = fakeOutput.getvalue().strip().split("\n")
for print_value in console:
self.assertTrue("Invalid" == print_value)
하나씩 천천히 살펴보겠습니다.
test case를 작성하기 위해서는 unittest.TestCase를 상속받는 클래스를 생성해야합니다.
→ 여기서는 UnitTest가 unittest.TestCase를 상속받고 있습니다.
또한 각 함수의 단위테스트를 정의할 때는 'test_함수명'으로 해야합니다.
→ 여기서는 main함수를 단위테스트하기 때문에 test_main으로 유닛테스트 함수명을 정의했습니다.
with patch('builtins.input', side_effect=["3", "1", "100", "0"]):
위 코드의 의미는 사용자로부터 입력받는 숫자를 "3", "1", "100", "0"로 iterable하게 지정해주겠다는 의미입니다.
위의 main 함수에서의 user_input = input("Input non-negative number : ") 부분에 4개의 값을 차례로 지정해주게 됩니다.
with patch('sys.stdout', new=StringIO()) as fakeOutput:
위 코드의 의미는 출력문을 fakeOutput 변수에 저장해주겠다는 의미입니다.
self.assertTrue("Valid" == print_value)
위 코드에서는 Valid값과 print_value 값이 다르면 AssertionError를 던지게 됩니다.
따라서 사용자가 "3", "1", "100", "0"를 입력했을 때 출력문으로 "Valid"가 잘 나오는지 단위테스트를 할 수 있습니다.
그 이후의 코드도 위와 똑같은 형식이므로 설명은 생략하겠습니다.
지금은 입력인자를 총 8개 밖에 정하지 않았지만 여러 방식을 통해(파일에서 값을 입력받는다든지, range문을 활용하여 값을 생성한다든지) 테스트 입력인자를 충분히 늘릴 수 있습니다.
직접 함수를 돌려보면서 print문을 확인하는 것보다 훨씬 효과적일 거라는 생각이 드네요.
'부스트캠프 AI Tech' 카테고리의 다른 글
[4주차 - Day15] F1 Score (0) | 2021.08.23 |
---|---|
[4주차 - Day15] VSCode ssh 접속 (0) | 2021.08.23 |
[2주차 - Day7] Gradient Descent Optimization Algorithms (0) | 2021.08.12 |
[1주차 - Day5] Entropy, Cross-entropy (0) | 2021.08.06 |
[1주차 - Day4] MLE(maximum likelihood estimation) (0) | 2021.08.06 |