Algorithm

λ°±μ€€ - μˆœμ—΄ 사이클(Swift)

CheonD 2022. 12. 3. 16:03

λ°±μ€€ - μˆœμ—΄ μ‚¬μ΄ν΄(Swift)

 

 

 λ¬Έμ œ μ„€λͺ…

 

https://www.acmicpc.net/problem/10451

 

10451번: μˆœμ—΄ 사이클

1λΆ€ν„° NκΉŒμ§€ μ •μˆ˜ N개둜 이루어진 μˆœμ—΄μ„ λ‚˜νƒ€λ‚΄λŠ” 방법은 μ—¬λŸ¬ κ°€μ§€κ°€ μžˆλ‹€. 예λ₯Ό λ“€μ–΄, 8개의 수둜 이루어진 μˆœμ—΄ (3, 2, 7, 8, 1, 4, 5, 6)을 배열을 μ΄μš©ν•΄ ν‘œν˜„ν•˜λ©΄ \(\begin{pmatrix} 1 & 2 &3&4&5&6&7&8 \\  3

www.acmicpc.net

 

 λ‚˜μ˜ 풀이

 

처음 문제λ₯Ό λ΄€μ„λ•ŒλŠ” μ™œ 3 2 7 8 1 4 5 6의 μˆœμ—΄μ΄ 였λ₯Έμͺ½μ²˜λŸΌλ˜λŠ”κ±΄μ§€ 이해λ₯Ό ν•˜μ§€ λͺ»ν–ˆλ‹€.

μ΄λŠ” κ²°κ΅­ 1λΆ€ν„°μ˜ μΈλ±μŠ€μ™€ 이 μˆ«μžλ“€κ°„μ— κ°„μ„ μ΄μžˆμŒμ„ λ‚˜νƒ€λ‚΄λŠ” κ²ƒμž„μ„ μ•Œμ•˜κ³  사이클이 λͺ‡κ°œ μ‘΄μž¬ν•˜λ©΄λ˜λŠ”μ§€λ₯Ό ν™•μΈν•˜λ©΄ 되기 λ•Œλ¬Έμ— μž¬κ·€λ°©λ²•μœΌλ‘œ 문제λ₯Ό ν•΄κ²°ν–ˆλ‹€.

 

ν•˜μ§€λ§Œ μ–΄λ– ν•œ 이유둜 μ‹œκ°„μ΄ˆκ³Όκ°€ λ‚˜μ„œ 문제λ₯Ό ν•΄κ²°ν•˜μ§€ λͺ»ν–ˆμ—ˆλŠ”λ° μ•„λž˜μ½”λ“œκ°€ λ‚˜μ˜ 처음 μ½”λ“œμ΄λ‹€.

 

import Foundation

let tc = Int(readLine()!)!
var visited = [Bool]()
var arr = [Int]()
var result = 0
func cycle(_ num: Int) {
    visited[num] = true
    if !visited[arr[num]] { cycle(arr[num]) }
}

for _ in 0..<tc {
    let N = Int(readLine()!)!
    arr = Array(repeating: 0, count: N+1)
    visited = Array(repeating: false, count: N+1)
    let input = readLine()!.components(separatedBy:" ").map{Int($0)!}
    for i in 1..<N+1 {
        arr[i] = input[i-1]
    }
    
    for i in 1..<N+1 {
        if !visited[i] {
            cycle(i)
            result += 1
        }
    }
    print(result)
    result = 0
}

 

cycleν•¨μˆ˜μ—μ„œ ν˜„μž¬ 탐색쀑인 값을 λ°©λ¬Έν‘œμ‹œν•˜κ³  κ·Έ 값이 κ°€λ¦¬ν‚€λŠ” 값이 λ°©λ¬Έλ˜μ§€μ•Šμ•˜λ‹€λ©΄ λ‹€μ‹œ μ‚¬μ΄ν΄ν•¨μˆ˜λ₯Ό ν˜ΈμΆœν•˜λŠ” λ°©μ‹μœΌλ‘œ μ½”λ“œλ₯Ό μž‘μ„±ν–ˆμ—ˆλŠ”λ° μ΄λŠ” μ‹œκ°„μ΄ˆκ³Όλ₯Ό 내기에 μ ν•©ν•œ μ½”λ“œμ˜€λ‹€. 

예λ₯Όλ“€μ–΄ cycleν•¨μˆ˜κ°€ μ—°μ†μœΌλ‘œ 500번 ν˜ΈμΆœλ˜μ—ˆλ‹€κ³  κ°€μ •ν•΄λ³΄μž.

κ·Έλ ‡λ‹€λ©΄ μ²«λ²ˆμ§ΈλΆ€ν„° 500λ²ˆμ§ΈκΉŒμ§€ λ°©λ¬Έλ˜μ§€ μ•Šμ€ κ°’λ“€μ΄μ—ˆλ‹€λŠ” 것인데 μ΄λŠ” 501λ²ˆμ§Έμ— λ°©λ¬Έν–ˆλ˜ κ²ƒμ΄μ—ˆλ‹€λ©΄ λ°”λ‘œ λͺ¨λ“  사이클이 μ’…λ£Œκ°€ λ˜λŠ”κ²ƒμ΄ μ•„λ‹ˆλΌ 500, 499, 498번째의 ν•¨μˆ˜κ°€ 순차적으둜 λλ‚˜λ©΄μ„œ μ’…λ£Œν•˜κ²Œ λœλ‹€. 

즉 ν•¨μˆ˜μ•ˆμ— ν•¨μˆ˜μ•ˆμ— ν•¨μˆ˜κ°€ μžˆλŠ” ν˜•νƒœμ˜€λ˜ 것이닀. 

 

이λ₯Ό λ‹€μŒμ˜ μ½”λ“œλ‘œ ν•΄κ²°ν•  수 μžˆλ‹€.

λ°©λ¬Έλ˜μ—ˆλ‹€λ©΄ λ°”λ‘œ return trueλ₯Ό 쀌으둜써 ν•¨μˆ˜λ₯Ό μ’…λ£Œμ‹œν‚¬ 수 있고, λ°©λ¬Έλ˜μ§€μ•Šμ€ μƒνƒœλΌλ©΄ return ν•¨μˆ˜λ₯Ό 쀌으둜써 ν•¨μˆ˜μ•ˆμ— ν•¨μˆ˜κ°€ μžˆλŠ” 것이 μ•„λ‹Œ μƒˆλ‘œμš΄ ν•¨μˆ˜λ‘œ μŠ€μ½”ν”„κ°€ μ΄λ™λ˜κ²Œ λ§Œλ“€ 수 μžˆλ‹€. 

 

import Foundation

let tc = Int(readLine()!)!
var visited = [Bool]()
var arr = [Int]()
var result = 0
func cycle(_ num: Int) -> Bool {
    visited[num] = true
    if visited[arr[num]] { return true }
    return cycle(arr[num])
}

for _ in 0..<tc {
    let N = Int(readLine()!)!
    arr = Array(repeating: 0, count: N+1)
    visited = Array(repeating: false, count: N+1)
    let input = readLine()!.components(separatedBy:" ").map{Int($0)!}
    for i in 1..<N+1 {
        arr[i] = input[i-1]
    }
    
    for i in 1..<N+1 {
        if !visited[i] {
            if cycle(i) {
                result += 1
            }
        }
    }
    print(result)
    result = 0
}