๊ธ€ ์ž‘์„ฑ์ž: ๊ฐœ๋ฐœํ•˜๋Š” ํ›ˆ์ด

ํ (Queue)

ํ๋Š” FIFO(First In First Out)์˜ ํŠน์„ฑ์„ ๊ฐ€์ง€๋Š” ์ž๋ฃŒ๊ตฌ์กฐ์ž…๋‹ˆ๋‹ค. ์ด๋ฆ„์ฒ˜๋Ÿผ ๊ฐ€์žฅ ๋จผ์ € ๋„ฃ์€ ๋ฐ์ดํ„ฐ๋ฅผ ๊ฐ€์žฅ ๋จผ์ € ๊บผ๋‚ด๋Š” ํŠน์ง•์„ ๊ฐ€์ง€๊ณ  ์žˆ์Šต๋‹ˆ๋‹ค. ์Šค์œ„ํ”„ํŠธ์—์„œ๋Š” ๋ฐฐ์—ด์—์„œ removeFirst๋ฅผ ์ง€์›ํ•˜๊ธด ํ•˜์ง€๋งŒ,

์ด๋ ‡๊ฒŒ ์‹œ๊ฐ„๋ณต์žก๋„๋Š” O(n)์ด๋ผ์„œ, ๋™์ž‘๋งŒ FIFO์ผ ๋ฟ, ์‚ญ์ œ์— O(1)์„ ๋ณด์žฅํ•˜๋Š” ํ๊ฐ€ ๋  ์ˆ˜๋Š” ์—†์Šต๋‹ˆ๋‹ค. ๊ทธ๋ž˜์„œ ์ด ํฌ์ŠคํŠธ์—์„œ๋Š” ๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ๋ฅผ ์‚ฌ์šฉํ•ด์„œ ํ๋ฅผ ๊ตฌํ˜„ํ•˜๋„๋ก ํ•˜๊ฒ ์Šต๋‹ˆ๋‹ค.

 

๋ผˆ๋Œ€ ๋งŒ๋“ค๊ธฐ

var list = TwoPointerLinkedList<T>()
    
init(_ elements: [T] = []) {
    for element in elements {
        list.add(node: Node(data: element))
    }
}
    
var count : Int {
    return list.count
}
var isEmpty : Bool {
    return list.head == nil
}
var front: T? {
    return list.front?.data
}
var back: T? {
    return list.back?.data
}

๋จผ์ € ๊ธฐ๋ณธ์ ์ธ ํ”„๋กœํผํ‹ฐ์™€ ์ƒ์„ฑ์ž๋Š” ์ด๋ ‡๊ฒŒ ๊ตฌ์„ฑํ–ˆ์Šต๋‹ˆ๋‹ค. TwoPointerLinkedList๋Š” head, tail ๋‘ ๊ฐœ์˜ ํฌ์ธํ„ฐ๋กœ ๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ์˜ ๊ฐ€์žฅ ์•ž๊ณผ ๋’ค๋ฅผ ๊ฐ€๋ฆฌํ‚ค๊ฒŒ ํ•˜๋Š” ๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ ์ž๋ฃŒ๊ตฌ์กฐ์ž…๋‹ˆ๋‹ค.

 

์ƒ์„ฑ์ž์—์„œ๋Š” ๋งŒ์•ฝ์— ๋ฐฐ์—ด์ด ํ•œ ๋ฒˆ์— ๋“ค์–ด์˜ค๋ฉด ์ˆœ์„œ๋Œ€๋กœ ๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ์— ์ถ”๊ฐ€ํ•ด์ฃผ๋Š” ๋กœ์ง์„ ๋„ฃ์–ด๋‘์—ˆ๊ณ , count ํ”„๋กœํผํ‹ฐ๋Š” ๋…ธ๋“œ์˜ ๊ฐœ์ˆ˜๋ฅผ, isEmpty ํ”„๋กœํผํ‹ฐ๋Š” head ํฌ์ธํ„ฐ๊ฐ€ ๋น„์–ด์žˆ๋Š”์ง€๋ฅผ ํ†ตํ•ด ๊ฐ’์„ ๋ฐ˜ํ™˜ํ•˜๋„๋ก ๊ตฌ์„ฑํ–ˆ์Šต๋‹ˆ๋‹ค.

 

๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ

ํ๋ฅผ ๋งŒ๋“ค๊ธฐ ์œ„ํ•ด์„œ ๋งŒ๋“  ๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ๋Š” ์ด๋ ‡์Šต๋‹ˆ๋‹ค! ๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ์˜ ๊ตฌํ˜„๊ณผ ๋™์ž‘๋ฐฉ์‹์€ https://jeonyeohun.tistory.com/320 ์—ฌ๊ธฐ์— ๋” ์ž์„ธํžˆ ์„ค๋ช…๋˜์–ด ์žˆ์Šต๋‹ˆ๋‹ค!

import Foundation

struct TwoPointerLinkedList<T> {
    var head: Node<T>?
    var tail: Node<T>?
    var count: Int = 0
    
    var front: Node<T>? {
        return head
    }
    var back: Node<T>? {
        return tail
    }
    
    mutating func add(node: Node<T>) {
        if self.head == nil {
            self.head = node
            self.tail = node
        } else {
            self.tail?.next = node
            self.tail = node
        }
        self.count += 1
    }
    mutating func removeFirst() -> Node<T>? {
        guard head != nil else {
            self.clear()
            return nil
        }
        let deleted = self.head
        self.head = head?.next
        self.count -= 1
        
        if head == nil {
            self.clear()
        }
        return deleted
    }
    mutating func clear() {
        self.head = nil
        self.tail = nil
    }
}

๊ธฐ์กด ๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ์™€ ๊ฑฐ์˜ ๋™์ผํ•˜์ง€๋งŒ, clear ๋ฉ”์„œ๋“œ๋ฅผ ํ†ตํ•ด ๋ชจ๋“  ๋…ธ๋“œ๋ฅผ ํ•œ๋ฒˆ์— ํ•ด์ œํ•  ์ˆ˜ ์žˆ๊ฒŒ ํ•˜๊ณ , ๋…ธ๋“œ์˜ ๊ฐœ์ˆ˜๋ฅผ ํƒ์ƒ‰์—†์ด ํ™•์ธํ•  ์ˆ˜ ์žˆ๋„๋ก ํ•˜๋Š” count ํ”„๋กœํผํ‹ฐ์™€ ๊ฐ€์žฅ ์•ž ๋…ธ๋“œ์™€ ๊ฐ€์žฅ ๋’ค ๋…ธ๋“œ๋ฅผ ์‰ฝ๊ฒŒ ํ™•์ธํ•  ์ˆ˜ ์žˆ๋Š” front, back ํ”„๋กœํผํ‹ฐ๋ฅผ ์ถ”๊ฐ€ํ–ˆ์Šต๋‹ˆ๋‹ค.

์‚ฝ์ž…(push) - O(1)

์‚ฝ์ž… ์—ฐ์‚ฐ์€ ๊ธฐ์กด์˜ ๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ์˜ ์ถ”๊ฐ€ ์—ฐ์‚ฐ์„ ๊ทธ๋Œ€๋กœ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

    mutating func push(_ element: T) {
        list.add(node: Node(data: element))
    }

์ด๋ฒˆ์—๋Š” ํ๋ฅผ ์ข€ ๋” ๋ฒ”์šฉ์ ์œผ๋กœ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๊ฒŒ, ๋…ธ๋“œ๋ฅผ ์™ธ๋ถ€์—์„œ ๋งŒ๋“ค์–ด์„œ ๋„ฃ๋Š” ๊ฒƒ์ด ์•„๋‹ˆ๋ผ ํ ์ž๋ฃŒ๊ตฌ์กฐ์—์„œ ์ž์ฒด์ ์œผ๋กœ ๋งŒ๋“ค์–ด์„œ ๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ์— ์ฃผ์ž…ํ•˜๋Š” ๋ฐฉ์‹์œผ๋กœ ๊ตฌ์„ฑํ•ด๋ณด์•˜์Šต๋‹ˆ๋‹ค.

 

๋ฆฌ์ŠคํŠธ ๋‚ด๋ถ€์—๋Š”,

mutating func add(node: Node<T>) {
    if self.head == nil {
        self.head = node
        self.tail = node
    } else {
        self.tail?.next = node
        self.tail = node
    }
    self.count += 1
}

์ด๋ ‡๊ฒŒ ์ƒˆ๋กœ์šด ๋…ธ๋“œ๋ฅผ tail ๋’ค์— ๋ถ™์—ฌ์ฃผ๊ฑฐ๋‚˜, ๋ฆฌ์ŠคํŠธ๊ฐ€ ๋น„์–ด์žˆ๋Š” ๊ฒฝ์šฐ์—๋Š” ์ถ”๊ฐ€ํ•ด์ฃผ๋Š” ๋กœ์ง๊ณผ ๋…ธ๋“œ์˜ ๊ฐœ์ˆ˜๋ฅผ ๋Š˜๋ ค์ฃผ๋Š” ๋กœ์ง์ด ๋“ค์–ด๊ฐ€์žˆ์Šต๋‹ˆ๋‹ค. ๋ณ„๋„์˜ ํƒ์ƒ‰๊ณผ์ • ์—†์ด tail๋กœ ์ฐพ์•„๊ฐ€ ๋’ค์— ๋…ธ๋“œ๋ฅผ ์ถ”๊ฐ€ํ•ด์ฃผ๋Š” ๋ฐฉ์‹์ด๊ธฐ ๋•Œ๋ฌธ์— O(1)์˜ ์‹œ๊ฐ„๋ณต์žก๋„๊ฐ€ ๋ณด์žฅ๋ฉ๋‹ˆ๋‹ค.

 

์‚ญ์ œ(pop) - O(1)

์‚ญ์ œ ์—ฐ์‚ฐ์€ ๋งํฌ๋“œ ๋ฆฌ์ŠคํŠธ์—์„œ ๊ฐ€์žฅ ์•ž ๋…ธ๋“œ๋ฅผ ๋ฐ˜ํ™˜ํ•˜๊ณ  ์ง€์šฐ๋Š” ๋ฐฉ์‹์œผ๋กœ ๊ตฌํ˜„๋˜์–ด ์žˆ๋Š”๋ฐ์š”,

์ด๋ ‡๊ฒŒ ๋ฆฌ์ŠคํŠธ๊ฐ€ ์žˆ์„ ๋•Œ, 

ํ˜„์žฌ head ๊ฐ€ ๊ฐ€๋ฆฌํ‚ค๋Š” ๊ฐ’์„ ๋ณ€์ˆ˜์— ์ž„์‹œ๋กœ ์ €์žฅํ•ด ๋ฉ”๋ชจ๋ฆฌ์—์„œ ํ•ด์ œ๋˜์ง€ ์•Š๋„๋ก ๊ฐ•ํ•œ ์ฐธ์กฐ๋ฅผ ํ•ด์ฃผ๊ณ ,

head ํฌ์ธํ„ฐ๋ฅผ ํ•œ ์นธ ์•ž์œผ๋กœ ์ด๋™์‹œ์ผœ์„œ ๋ฆฌ์ŠคํŠธ์—์„œ ๊ฐ€์žฅ ์•ž์— ์žˆ๋˜ ๋…ธ๋“œ๋ฅผ ์ œ์™ธ์‹œ์ผœ์ค๋‹ˆ๋‹ค. ๊ทธ๋ฆฌ๊ณ  ์ž„์‹œ๋กœ ์ €์žฅํ–ˆ๋˜ ๋…ธ๋“œ๋ฅผ ๊ทธ๋Œ€๋กœ ๋ฐ˜ํ™˜ํ•˜๋ฉด pop ์—ฐ์‚ฐ์ด ์™„์„ฑ๋ฉ๋‹ˆ๋‹ค. ์ด๋ ‡๊ฒŒ ํ•˜๋ฉด ํƒ์ƒ‰ ์—†์ด ๊ณง๋ฐ”๋กœ ์ฒซ๋ฒˆ์งธ ๋…ธ๋“œ๋ฅผ ์ง€์šฐ๊ณ  ๋ฐ˜ํ™˜ํ•˜๋‹ˆ O(1)์˜ ์‹œ๊ฐ„๋ณต์žก๋„๊ฐ€ ๋ณด์žฅ๋ฉ๋‹ˆ๋‹ค.

 

mutating func removeFirst() -> Node<T>? {
    guard head != nil else {
        self.clear()
        return nil
    }
    let deleted = self.head
    self.head = head?.next
    self.count -= 1
    
    if head == nil {
        self.clear()
    }
    return deleted
}

 

์ „์ฒด ์ฝ”๋“œ

 

 

 

GitHub - jeonyeohun/Data-Structures-In-Swift: ๐Ÿ‘ท๐Ÿป‍โ™‚๏ธ STL ์™œ ์—†์–ด.. ์Šค์œ„ํ”„ํŠธ๋กœ ๊ตฌํ˜„ํ•˜๋Š” ์ž๋ฃŒ๊ตฌ์กฐ

๐Ÿ‘ท๐Ÿป‍โ™‚๏ธ STL ์™œ ์—†์–ด.. ์Šค์œ„ํ”„ํŠธ๋กœ ๊ตฌํ˜„ํ•˜๋Š” ์ž๋ฃŒ๊ตฌ์กฐ. Contribute to jeonyeohun/Data-Structures-In-Swift development by creating an account on GitHub.

github.com

์ž๋ฃŒ๊ตฌ์กฐ ์‹œ๋ฆฌ์ฆˆ์˜ ์ฝ”๋“œ๋“ค์€ ์ด ๋ ˆํฌ์—์„œ ๋ชจ๋‘ ํ™•์ธํ•  ์ˆ˜ ์žˆ์–ด์š”!