Home 덱 Deque
Post
X

덱 Deque

덱에 대해 알아보자.


덱 (Deque, Double-Ended Queue)

덱은 앞(front)과 뒤(rear) 양쪽에서 모두 삽입과 삭제가 가능한 큐 자료구조입니다.

deque


덱의 추상 자료형 ADT

  • pushFront(x) : 맨 앞에 새로운 요소 삽입
  • pushBack(x) : 맨 마지막에 새로운 요소 삽입
  • popFront() : 맨 앞 요소 추출하고 반환
  • popBack() : 맨 마지막 요소 추출하고 반환
  • peekFront() : 맨 앞 요소 조회
  • peekBack() : 맨 마지막 요소 조회
  • isEmpty() : 비어있는지 확인

  • size() : 요소 갯수 반환

구현 코드

시간복잡도를 O(1)로 줄이기위해서 front, rear index를 사용합니다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
class Deque {
  constructor() {
    this.items = {};
    this.front = 0;
    this.rear = 0;
  }

  pushFront(value) {
    this.front--;
    this.items[this.front] = value;
  }

  pushBack(value) {
    this.items[this.rear] = value;
    this.rear++;
  }

  popFront() {
    if (this.isEmpty()) {
      throw new Error("Deque is empty");
    }

    const value = this.items[this.front];
    delete this.items[this.front];
    this.front++;

    if (this.isEmpty()) {
      this.front = 0;
      this.rear = 0;
    }

    return value;
  }

  popBack() {
    if (this.isEmpty()) {
      throw new Error("Deque is empty");
    }

    this.rear--;

    const value = this.items[this.rear];
    delete this.items[this.rear];

    if (this.isEmpty()) {
      this.front = 0;
      this.rear = 0;
    }

    return value;
  }

  peekFront() {
    if (this.isEmpty()) {
      throw new Error("Deque is empty");
    }

    return this.items[this.front];
  }

  peekBack() {
    if (this.isEmpty()) {
      throw new Error("Deque is empty");
    }

    return this.items[this.rear - 1];
  }

  size() {
    return this.rear - this.front;
  }

  isEmpty() {
    return this.front === this.rear;
  }
}

pushFront

맨 앞에 새로운 요소를 추가하는 것으로 front 값을 감소시킨 후 해당 위치에 요소를 추가합니다.

1
2
3
4
5
deque.pushFront(1);
deque.pushFront(2);
deque.pushFront(3);

console.log(deque); // { items: { '0': 1, '1': 2, '2': 3 }, front: 0, rear: 3 }

pushBack

맨 마지막에 새로운 요소를 추가하는 것으로 rear index 위치에 요소를 추가한 후 rear 값을 증가합니다.

rear 값은 다음에 삽입할 위치를 가리키는 포인터(Exclusive End)

1
2
3
4
5
deque.pushBack(1);
deque.pushBack(2);
deque.pushBack(3);

console.log(deque); // { items: { '0': 1, '1': 2, '2': 3 }, front: 0, rear: 3 }

popFront

맨 앞 요소를 추출하는 것으로 front index 위치에 요소를 추출한 후 front 값을 증가시킵니다.

추출한 후 덱이 비어있다면 front, rear 값을 0으로 초기화

1
2
3
4
5
6
7
8
9
10
deque.pushFront(1);
deque.pushFront(2);
deque.pushFront(3);

console.log(deque); // { items: { '0': 1, '1': 2, '2': 3 }, front: 0, rear: 3 }

deque.popFront(); // 3 (front : -2, rear : 0)
deque.popFront(); // 2 (front : -1, rear : 0)

console.log(deque); // { items: { '-1': 1 }, front: -1, rear: 0 }

popBack

맨 마지막 요소를 추출하는 것으로 rear 값을 감소시킨 후 rear index 위치에 요소를 추출합니다.

추출한 후 덱이 비어있다면 front, rear 값을 0으로 초기화

1
2
3
4
5
6
7
8
9
10
deque.pushFront(1);
deque.pushFront(2);
deque.pushFront(3);

console.log(deque); // { items: { '0': 1, '1': 2, '2': 3 }, front: 0, rear: 3 }

deque.popBack(); // 1 (front : -3, rear : -1)
deque.popBack(); // 2 (front : -3, rear : -2)

console.log(deque); // { items: { '-3': 3 }, front : -3, rear : -2 }

peekFront

맨 앞 요소를 확인합니다.

1
2
3
4
5
deque.pushFront(1);
deque.pushFront(2);
deque.pushFront(3);

console.log(deque.peekFront()); // 3

peekBack

맨 마지막 요소를 확인합니다.

1
2
3
4
5
deque.pushFront(1);
deque.pushFront(2);
deque.pushFront(3);

console.log(deque.peekBack()); // 1

isEmpty

큐 안에 요소가 있는 지 확인합니다.

front === rear

1
2
3
4
5
deque.isEmpty(); // true

deque.pushFront(1);

deque.isEmpty(); // false

size

덱 안에 있는 요소들의 갯수를 반환합니다.

rear - front

1
2
3
4
5
deque.pushFront(1);
deque.pushFront(2);
deque.pushFront(3);

deque.size(); // 3
이 기사는 저작권자의 CC BY 4.0 라이센스를 따릅니다.