[알고리즘] Swift 두 정수 사이의 합

이유진·2024년 3월 20일
0

알고리즘

목록 보기
22/32

문제 설명

두 정수 a, b가 주어졌을 때 a와 b 사이에 속한 모든 정수의 합을 리턴하는 함수, solution을 완성하세요.

예를 들어 a = 3, b = 5인 경우, 3 + 4 + 5 = 12이므로 12를 리턴합니다.


제한 조건

  • a와 b가 같은 경우는 둘 중 아무 수나 리턴하세요.
  • a와 b는 -10,000,000 이상 10,000,000 이하인 정수입니다.
  • a와 b의 대소관계는 정해져있지 않습니다.

입출력 예

abreturn
3512
333
5312

풀이 과정

일단 처음으로 풀어봤던 과정!

  1. 두 정수 a,b의 크기를 비교한다.(a와 b 중 작은 값부터 범위를 시작해야 하기 때문에!)
    1) a가 b보다 큰 경우 2)b가 a보다 큰 경우 3)a와 b가 같은 경우
  2. if, else if, else를 사용해 경우에 따라 각각 다른 값을 반환할 수 있도록 한다.
  3. 모든 값을 더하는 과정은 for문을 사용했다!
  4. Int를 Int64 타입으로 변환해서 반환해줘야 하는 것 잊지 않기 - !

Solution

func solution(_ a:Int, _ b:Int) -> Int64 {
    var sum: Int64 = 0
    
    if a > b {
        for i in b...a {
            sum += Int64(i)
        }
    } else if a < b {
        for i in a...b {
              sum += Int64(i)
        }
    } else {
        sum = Int64(a)
    }
        return sum   
}

문제점

테스트 케이스는 전부 통과했고, 정답 인정은 됐는데 찝찝한 부분이 있었다.

테스트 4 ~ 10까지의 실행 시간이 엄청 길더라..!
정수 a, b 의 크기에 따라 반복되는 횟수가 많아져서 그런 것 같다.

다르게 작성해본 코드들도 있는데,
모두 반복 과정이 있어서 여전히 테스트 4 ~ 10까지의 실행 시간이 길었다.
심지어 클로저를 사용했을 때는 테스트 4에서 시간 초과 실패가 떴다.

실패했지만..! 실행 시간은 길지만..! 일단 코드는 남겨본다.

1.클로저 사용

func solution(_ a:Int, _ b:Int) -> Int64 {
    var sum: Int64 = 0
    
    if a > b {
        sum = (b...a).reduce(0) { $0 + Int64($1) }
    } else if a < b {
        sum = (a...b).reduce(0) { $0 + Int64($1)}
    } else {
        sum = Int64(a)
    }
        return sum   
}

이렇게 실패가 떴다ㅠ0ㅜ

2. max와 min
이건 새로 사용해본 개념!
Swift 표준 라이브러리에서 제공되는 함수라고 한다.
max( , )는 주어진 두 값을 비교해서 더 큰 값을 반환하고,
min( , )는 주어진 두 값을 비교하여 더 작은 값을 반환한다.

그러니까 max(a, b) 를 하면 a, b 중 큰 값 반환,
min(a, b)를 하면 a, b 중 작은 값을 반환하게 되는 것!

이걸 활용해 코드를 짜면 if, else if, else를 사용할 때보다 좀 더 간결한 코드를 작성할 수 있다.

func solution(_ a:Int, _ b:Int) -> Int64 {

    let start = min(a, b)
    let end = max(a, b)
    var sum: Int64 = 0
    
    for i in start...end {
        sum += Int64(i)
    }
    return sum
}

하지만 위에서 말했 듯 실행 시간은 여전히 길다 :>
더하는 과정이 반복되기 때문에 a와 b 사이의 길이가 길어질 수록
반복하는 과정도 함께 늘어나고 늘어나고 늘어나고..~..~~~


Better Solution

다른 풀이들 보면서 알게 된 더 효율적인 코드.

반복문이 아닌 a와 b 사이 모든 정수의 합을 구하는 공식인
(a + b) * ( b - a +1 ) / 2 를 사용해주면 된다.

func solution(_ a:Int, _ b:Int) -> Int64 {
    let start = min(a, b)
    let end = max(a, b)
    let count = end - start + 1
    let sum = Int64((start + end) * count / 2)
    return sum
}

/*
let count = end - start + 1
- 'end - start' 는 두 정수 end와 start 사이의 간격
- 이렇게 하면 a부터 b까지의 모든 정수 갯수에서 -1 된 값이 된다.
- 따라서 +1을 해주어 시작값~끝값 범위에 있는 모든 정수 갯수를 카운트 하도록 한다!
*/

더 줄이면 이렇게!

func solution(_ a: Int, _ b: Int) -> Int64 {
    return Int64((a + b) * (max(a, b) - min(a, b) + 1) / 2)
}

이렇게 하면 값을 더하는 과정을 반복하지 않고도 두 정수와 두 정수 사이의 값을 모두 더한 값을 구할 수 있다.
실행 시간 완전 단축 됨!

2개의 댓글

comment-user-thumbnail
2024년 3월 20일

오 다양한 풀이를!!! 저보다 더 코딩을 잘 하시는 것 같아요!! 잘 보고 갑니다! 파이팅

답글 달기
comment-user-thumbnail
2024년 3월 20일

한가지의 문제로 다양한 방향으로 문제 풀이를 시도하는 것 자체가 정말 좋은 학습법 같아요! 본받게 되네요~! 오늘도 수고많으셨습니다ㅎ

답글 달기