코드트리 블로그 챌린지 글을 계속 이어나가기 위해 제목과 시리즈 이름을 바꿔서 진행합니다.
어제 봤던 문제와 같은 문제들이 많아서 1문제 빼고 다풀었다!
하나는 정수형 숫자들 나열하는 문젠데 한번 찾아봐야겠다.
코드를 짤 때에는 효율성
을 많이 따지게 된다. 그래서 우리는 일단 시간 복잡도
에 대해 알아 볼 것이다.
우리가 맨 처음 풀었던 문제들을 보면 대부분 루프를 사용하지 않은 단순 연산하는 문제들을 마주친다.
예를 들어,
a = a+1
print(a)
라는 코드를 본다면, a
변수에는 한번의 단순한 연산(덧셈)을 실행하므로 O(1)
의 시간복잡도라고 가정하며, 마찬가지로, print
와 같은 메서드도 단순히 출력하므로 O(1)
의 시간복잡도라고 가정한다.
1초
에 1억번
for문
을 통해 단순 연산을 해야 1초
가 나온다.1초
~ 10초
정도 시간 제한이 걸려 있다.그래서 우리는 코딩 테스트 문제에 적혀 있는 자료의 양
을 보고 어느 정도 수행시간 이하를 요구하는 지 파악해야 한다.(그래야 시간초과
가 나오지 않는다.)
예를 들어, 자료의 양이 10만개
정도라면, O(nlogn)
이하의 시간 복잡도를 요구한다. 그래야 연산하는데 1억번
보다 적게 나오기 때문이다.
오메가 표기법
은 실제 코드보다 빠르다고 파악해 버릴 수 있기 때문에 효율성을 파악하는데 위험하고, 세타 표기법
은 실제 코드가 정확히 해당 시간 복잡도를 나타내기 어렵기 때문에 빅오 표기법이 최악의 경우를 판단해 가장 안전하게 시간 복잡도를 나타낼 수 있기 때문이라고 한다.
링크: https://www.codetree.ai/missions/6/problems/time-complexity-3?&utm_source=clipboard&utm_medium=text
위의 코드를 먼저 보면,
i
가 n^2
번 돌아가는 동안
k
는 i
번 돌아간다.
j
는 n
번 돌아간다.
이런 상태인데, 여기서 i
번 돌아가는 것은 해당 이중 for문이 1, 2, 3 ... n^2번
돌아간다는 이야기다.
그래서 1
부터 n^2
까지 모두 더하면 (1+n^2)*(n^2)/2
가 나오는데, 이는 가장 큰 차수인 n^4
로 O(n^4)
라 할 수 있다.
아래의 코드는
i
가 n
번 돌아가는 동안
j
가 2씩 곱하면서 i
에 도달한다.
인데, 결론적으로 j
가 2씩 곱해지면 연산되는 횟수는 밑이 2인 로그
가 나오므로 O(nlogn)
이 나오게 된다.
코딩하는데 수행시간 뿐만 아니라 차지하는 메모리도 중요하다.
공간 복잡도도 점근적 표기법을 사용해 시간 복잡도 처럼 빅오 표기법을 사용한다.
공간 복잡도는 보통 리스트가 차지하는 가장 긴 길이를 보고 판단하는데, 메모리 128mb기준 가장 긴 리스트의 길이가 약 3천만을 넘지 않는다면 메모리초과와 같은 에러를 막을 수 있다.
만약 리스트가 3차원에 각 차원의 길이가 n인 리스트라면 공간복잡도는 O(n^3)이 된다.
https://velog.io/@gillog/%EC%8B%9C%EA%B0%84%EB%B3%B5%EC%9E%A1%EB%8F%84
https://www.acmicpc.net/board/view/24015