[알고리즘] Swift -프로그래머스 연습문제 #140108(문자열 나누기)

2023. 5. 28. 23:34ALGORITHM/Swift

728x90
반응형

 

문제링크

 

 

 

 

분석

문자열 s가 입력되었을 때 다음 규칙을 따라서 이 문자열을 여러 문자열로 분해하려고 한다.

먼저 첫 글자를 읽는다. 이를 x라고 가정한다.

이제 문자열을 왼쪽에서 오른쪽으로 읽어나가면서 x와 x가 아닌 다른 글자들이 나온 횟수를 각각 센다.

처음으로 두 횟수가 같아지는 순간 멈추고, 지금까지 읽은 문자열을 분리한다.

s에서 분리한 문자열을 빼고 남은 부분에 대해서 이 과정을 반복한다. 남은 부분이 없다면 종료한다.

만약 두 횟수가 다른 상태에서 더 이상 읽은 글자가 없다면, 역시 지금까지 읽은 문자열을 분리하고 종료한다.

문자열이 주어질 때 위 과정과 같이 문자열을 분해하고 분해한 문자열의 개수를 리턴하는 문제이다.

 

풀이 과정

처음에는 x와 x가 아닌 글자들의 횟수를 세는 줄 알고 예제를 봐도 결과가 나오지 않았다.

x가 아닌 글자들의 전체 횟수를 세는 것이 아닌 왼쪽부터 오른쪽으로 가면서 하나씩 세는 것이다.

예를 들어 banana의 경우를 보면

x= b일 때 b는 1개이고 a가 1개이기 때문에 두 횟수가 같아진다. b와 a를 문자열에서 분리한다.

그 다음 nana 에서 x=n 일 때, n은 1개이고 a도 1개이다. n과 a를 분리한다.

또, na 에서 x=n 일 때도 마찬가지이다.

 

마지막 예제인 aaabbaccccabba 를 보면

x=a 일 때 다음 문자열도 a 이고 다음도 a 이므로 a의 횟수는 3이 되고 그 다음으로 나오는 x가 아닌 글자는 b이다. a가 3개이고 b는 1개가 된다. b 다음이 b이므로 a가 3개이고 b가 2개 이므로 다음 글자를 확인한다. 

그 다음은 a이므로 x의 횟수는 4개가 된다. 그 다음으로는 c로 x가 아닌 글자들의 횟수는 b의 횟수와 c 1개의 횟수를 더한 3개가 된다. 그 다음의 c까지의 횟수는 이제 4개가 되어 x의 횟수와 x가 아닌 글자의 횟수가 같아진다. 이 때 문자열을 분리한다. aaabbacc 가 분리되게 된다.

그 다음 ccabba 에서 x= c가 된다. c의 횟수 2개 일 때, a 와 b까지 보면 x가 아닌 횟수가 2개가 되어 ccab가 분리된다.

 

먼저 가장 처음 x를 정해준 후 removefirst를 사용하여 왼쪽에 있는 글자와 비교한다.

var arr = Array(s)
var x = arr[0]
var xCnt = 0
var noCnt = 0

while !arr.isEmpty {
    let pop = arr.removeFirst()
    
    if x == pop {
        xCnt += 1
    } else {
        noCnt += 1
    }
}

x와 pop이 같을 경우는 x의 횟수를 증가시키고 아닐 경우에는 x가 아닌 글자의 횟수를 증가시킨다.

그리고 두 횟수가 같아질 경우에는 결과를 +1 한다. 그 다음 횟수를 다시 세어줘야 하기때문에 횟수를 세는 변수들은 0으로 초기화시켜준다.

var isTrue = false

if xCnt == noCnt || arr.isEmpty {
    result += 1
    isTrue = true
    (xCnt, noCnt) = (0, 0)
}

isTrue를 false로 지정한 후 횟수가 같아질 경우에 true로 변경하여 true일 때 x의 값이 변경되도록 지정하였다.

횟수가 다른 상태에서 배열이 비어있을 경우에도 결과값을 +1 해준다.

 

풀이

import Foundation

func solution(_ s:String) -> Int {
    var result = 0
    var arr = Array(s)
    var x = arr[0]
    var xCnt = 0
    var noCnt = 0
    var isTrue = false

    while !arr.isEmpty {
        let pop = arr.removeFirst()
        
        if isTrue {
            x = pop
            isTrue = false
        }
        
        if x == pop {
            xCnt += 1
        } else {
            noCnt += 1
        }
        
        if xCnt == noCnt || arr.isEmpty {
            result += 1
            isTrue = true
            (xCnt, noCnt) = (0, 0)
        }
    }
    
    return result
}

 

결과

print(solution( "abracadabra"            ))

 

 

 

 

 

728x90
반응형