카테고리 없음

스위프트 둘만의 암호

kingarthur 2024. 5. 31. 09:59

스위프트 둘만의 암호 문제풀기 

 

두 문자열 s와 skip, 그리고 자연수 index가 주어질 때, 다음 규칙에 따라 문자열을 만들려 합니다. 암호의 규칙은 다음과 같습니다.

  • 문자열 s의 각 알파벳을 index만큼 뒤의 알파벳으로 바꿔줍니다.
  • index만큼의 뒤의 알파벳이 z를 넘어갈 경우 다시 a로 돌아갑니다.
  • skip에 있는 알파벳은 제외하고 건너뜁니다.

예를 들어 s = "aukks", skip = "wbqd", index = 5일 때, a에서 5만큼 뒤에 있는 알파벳은 f지만 [b, c, d, e, f]에서 'b'와 'd'는 skip에 포함되므로 세지 않습니다. 따라서 'b', 'd'를 제외하고 'a'에서 5만큼 뒤에 있는 알파벳은 [c, e, f, g, h] 순서에 의해 'h'가 됩니다. 나머지 "ukks" 또한 위 규칙대로 바꾸면 "appy"가 되며 결과는 "happy"가 됩니다.

두 문자열 s와 skip, 그리고 자연수 index가 매개변수로 주어질 때 위 규칙대로 s를 변환한 결과를 return하도록 solution 함수를 완성해주세요.

 

제한사항

  • 5 ≤ s의 길이 ≤ 50
  • 1 ≤ skip의 길이 ≤ 10
  • s와 skip은 알파벳 소문자로만 이루어져 있습니다.
    • skip에 포함되는 알파벳은 s에 포함되지 않습니다.
  • 1 ≤ index ≤ 20

입출력 예

sskipindexresult

"aukks" "wbqd" 5 "happy"

 

일단 문제를 이해하는데 조금 걸린거 같다.

항상 문제를 대충보는 습관 때문에 그런거 같다. 아무튼 말이 이해가 잘 안된다 

 

어째든 내가 가진 문자안에 있으면 안되는 문자가 있으면 제외하고 주어진 숫자만큼 점프해서 출력한다 

즉 a 가 5칸 이동하면 b c d e f 라서 f 가 출력이지만 제외 해야하는 문자가 w b q d 이다 그래서 b d  제외하면 2개라 2칸 더 이동하면 h 

다음 u 같은 경우도 v w x y z 라서 z 출력이지만 w가 제외해야하는 문자라 1칸 더 이동해서 a를 출력 

암튼 이렇게 돌아간다. 

그래서 나는 유니코드를 쓰고 싶다는 생각에 알파벳 노가다로 치고 하면 쉬울것 같긴 했지만 

유니코드 저번에 사용해본 적이 있어서 사용해보기로 했다 . 

import Foundation

func solution(_ s:String, _ skip:String, _ index:Int) -> String {
    var zzz = [Int]()
    var krr = [Int]()
    for v in s.unicodeScalars {
        zzz.append(Int(v.value ))
    }
    for i in skip.unicodeScalars {
        krr.append(Int(i.value))
    }
    var sum = [[Int]]()
    for i in zzz {
        var zrr = [Int]()
        for j in krr {
            if i + 5 > j && i < j {
                zrr.append(1)
            } else {
                zrr.append(0)
            }
        }
        sum.append(zrr)
    }
    var p = [Int]()
    for i in sum {
        var e = 0
        for j in i {
            e += j
        }
        p.append(e)
    }
    var u = [Int]()
    for i in zzz.indices {
        u.append(zzz[i] + p[i] + index)
    }
    var m = String()
    for i in u {
        if i < 122 {
            m.append(String(Unicode.Scalar(i)!))
        } else {
            m.append(String(UnicodeScalar(i - 26)!))
        }
    }

    return m
}

solution("aukks", "wbqd", 5)

아직 배열에 대해 잘 다루지 못 해서 고생을 했다.

이중배열을 만들고 이중 배열을 벚겨내고 하는게 힘들었다. 

생각대로 작동이 안되서 ㅋㅋㅋ 아무튼 포문으로 하는 방법을 터득한거 같다.

 

처음 구현은 이렇게 했다. 일단 다시 더 간결하게 정리는 가능할거 같았으나 시간이 없어 일단 제출 햇는데

실패햇다 ㅋㅋㅋㅋㅋ 이유는 모르겠다  

//import Foundation
//
//func solution(_ k:Int, _ m:Int, _ score:[Int]) -> Int {
//    var scoreSort = score.sorted(by: >)
//    var answer = Array(repeating: Array(repeating: 0, count: m), count: scoreSort.count / m)
//    var count = 0
//    var sum = 0
//    for i in answer.indices {
//        for j in answer[i].indices {
//            answer[i][j] = scoreSort[count]
//            count += 1
//            sum += answer[i].min()! * m
//        }
//    }
//    return 0
//}
    
//
//    return stride(from: m-1, to: score.count, by: m).reduce(0) { $0 + scoreSort[$1] * m } //stride(from:through:by:) to 파라미터 포함시
//}
//
//solution(3, 4,  [1, 2, 3, 1, 2, 3, 1])

위에 방법 리피팅으로 반복해서 만드는 방법도 있으나 아직... 잘 적용방법을 모르겠다 포문하고 연동해서 

조만간 열심히 파해져서 돌아가는 방법을 알아야겠다. 

 

그래서 다른 사람들이 한걸 차용해봤다.

    let alphabet = "abcdefghijklmnopqrstuvwxyz".map { String($0) }
    var s = s.map { String($0) }
    
    for i in 0..<s.count {
        if var c = alphabet.firstIndex(of: s[i]) {
            var index = index
            
            while index != 0 {
                c += 1
                c %= 26
                
                if skip.contains(alphabet[c]) { continue }
                
                index -= 1
                s[i] = alphabet[c]
            }
        }
    }
    return s.joined()
}

 

내가 이렇게 풀기 싫어서 유니코드를 했지만 ㅋㅋㅋ

내꺼가 더 지저분한거 같다 암튼  더 간결한걸 찾아봤다. 

 

let arr = (0...25)
.map { String(UnicodeScalar($0 + 97)) }
.filter { !skip.contains($0) }

return s
.map {
    arr[arr.index(arr.firstIndex(of: String($0))!, offsetBy: index) % arr.count]
}
.joined()
}

 

간결한게 아주 마음에 든다 ㅎㅎ 다 아는 언어이지만 아직 사용을 잘 못하는 나 자신이 싫다 

완젼 사고력이 떨어지는거 같다 나는 문제를 많이 풀어봐야 할 것 같다. 언어 공부도 많이하고