▼ 문제 링크
Codility
Your browser is not supported You should use a supported browser. Read more
app.codility.com
# 풀이 1
내가 처음 푼 문제 풀이
func solution(_ A : inout [Int]) -> Int {
var left = 0
var right = 0
var index = 0
var result = 0
for i in 1..<A.count {
left = 0
right = 0
index = i
repeat {
index -= 1
left += A[index]
} while index > 0
index = i
repeat {
right += A[index]
index += 1
} while index < A.count
if i == 1 {
result = abs(left-right)
} else {
result = (result > abs(left-right) ? abs(left-right) : result)
}
}
return result
}
1. for문으로 1부터 마지막 요소까지를 기준으로 배열을 두 개로 나누고
2. 그 for문 안에서 왼쪽 배열과 오른쪽 배열의 각각의 총합을 구한다.
3. 왼쪽 배열 합과 오른쪽 배열 합의 차를 계산하고
4. 그 결과를 이전 결과와 비교해서 더 작은 값을 반환한다.
위 코드는 로직은 맞았으나 시간 복잡도가 O(N*N)으로 퍼포먼스 테스트에서 타임아웃 에러가 떴다. 🥲
그래서 조금이라도 반복문을 돌리는 횟수를 줄여보려고 발악을 해 본 게 아래 코드
# 풀이 2
두 개로 나눈 배열의 합의 차는 (전체 합 - 뺄 배열의 합*2)라는 식을 이용한 코드
func solution(_ A : inout [Int]) -> Int {
var totalSum = 0
var devidedSum = 0
var index = 0
var result = 0
var absSubtraction = 0
A.forEach {
totalSum += $0
}
for i in 1..<A.count {
index = i
devidedSum = 0
if i <= A.count/2 {
repeat {
index -= 1
devidedSum += A[index]
} while index > 0
} else {
repeat {
devidedSum += A[index]
index += 1
} while index < A.count
}
absSubtraction = abs(totalSum - devidedSum*2)
if i == 1 {
result = absSubtraction
} else {
result = (result < absSubtraction ? result : absSubtraction)
}
}
return result
}
전체적인 코드는 풀이 1과 비슷하지만, 여기서는 두 배열의 합을 각각 구하지 않고 한쪽 배열의 합만 구한 뒤 해당 값의 2배를 빼는 방법을 사용했다. 하지만 돌리는 while문 횟수가 아주 조금 줄어들었을 뿐 전체적으로 큰 변화는 없었고, 풀이 1과 마찬가지로 타임아웃 에러를 받았다. 퉤...
대체 시간 복잡도는 어떻게 줄이는데?! 하고 풀이를 찾아다녔고 세상엔 똑똑한 사람들이 참 많다. 사실 풀이를 보고 나면 바로 이해가 가는데 왜 혼자서는 답이 안떠오르는지...🤦
# 풀이 3
똑똑한 천재들의 풀이 방법 베끼기
func solution(_ A : inout [Int]) -> Int {
var leftSum = 0
var rightSum = 0
A.forEach {
rightSum += $0
}
var difference = 0
var result = 0
for i in 1..<A.count {
leftSum += A[i-1]
rightSum -= A[i-1]
difference = abs(leftSum-rightSum)
if i == 1 {
result = difference
} else {
result = (result > difference ? difference : result)
}
}
return result
}
이전 풀이들과 달리, 굳이 행렬의 합을 while문 안에서 한꺼번에 구할 필요가 없었다! for문 하나만으로도 충분히 두 배열의 합과 그 차를 각각 구할 수 있었고, 시간 복잡도는 O(N)으로 훨씬 줄어들었다. 풀이 1, 2에서는 최대 2.060초가 걸리던 게 0.036초로 어마어마하게 줄었더라...🙃
'Algorithm' 카테고리의 다른 글
[프로그래머스] 멀쩡한 사각형 - 최대공약수 구하기 (0) | 2021.07.27 |
---|---|
[코딜리티] MaxDoubleSliceSum (0) | 2021.07.23 |
[프로그래머스] 정렬 - 가장 큰 수 (0) | 2021.07.11 |
[코딜리티] Stone Wall - Stack과 Queue (0) | 2021.07.01 |
[프로그래머스] 짝지어 제거하기 - 효율성 통과하기 (0) | 2021.06.29 |