Files
hello-algo/ru/codes/c/chapter_stack_and_queue/array_deque.c
Yudong Jin 772183705e Add ru version (#1865)
* Add Russian docs site baseline

* Add Russian localized codebase

* Polish Russian code wording

* Update ru code translation.

* Update code translation and chapter covers.

* Fix pythontutor extraction.

* Add README and landing page.

* placeholder of profiles

* Use figures of English version

* Remove chapter paperbook
2026-03-28 04:24:07 +08:00

172 lines
6.5 KiB
C
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
/**
* File: array_deque.c
* Created Time: 2023-03-13
* Author: Gonglja (glj0@outlook.com)
*/
#include "../utils/common.h"
/* Двусторонняя очередь на основе кольцевого массива */
typedef struct {
int *nums; // Массив для хранения элементов очереди
int front; // Указатель head, указывающий на первый элемент очереди
int queSize; // Указатель хвоста, указывающий на позицию после хвоста
int queCapacity; // Вместимость очереди
} ArrayDeque;
/* Конструктор */
ArrayDeque *newArrayDeque(int capacity) {
ArrayDeque *deque = (ArrayDeque *)malloc(sizeof(ArrayDeque));
// Инициализация массива
deque->queCapacity = capacity;
deque->nums = (int *)malloc(sizeof(int) * deque->queCapacity);
deque->front = deque->queSize = 0;
return deque;
}
/* Деструктор */
void delArrayDeque(ArrayDeque *deque) {
free(deque->nums);
free(deque);
}
/* Получить вместимость двусторонней очереди */
int capacity(ArrayDeque *deque) {
return deque->queCapacity;
}
/* Получение длины двусторонней очереди */
int size(ArrayDeque *deque) {
return deque->queSize;
}
/* Проверка, пуста ли двусторонняя очередь */
bool empty(ArrayDeque *deque) {
return deque->queSize == 0;
}
/* Вычислить индекс в кольцевом массиве */
int dequeIndex(ArrayDeque *deque, int i) {
// С помощью операции взятия остатка соединить начало и конец массива
// Когда i выходит за хвост массива, вернуться к началу
// Когда i выходит за голову массива, вернуться к концу
return ((i + capacity(deque)) % capacity(deque));
}
/* Добавление в голову очереди */
void pushFirst(ArrayDeque *deque, int num) {
if (deque->queSize == capacity(deque)) {
printf("Дек заполнен\r\n");
return;
}
// Указатель головы сместить влево на одну позицию
// С помощью операции взятия остатка реализовать возврат front к хвосту после выхода за начало массива
deque->front = dequeIndex(deque, deque->front - 1);
// Добавить num в голову очереди
deque->nums[deque->front] = num;
deque->queSize++;
}
/* Добавление в хвост очереди */
void pushLast(ArrayDeque *deque, int num) {
if (deque->queSize == capacity(deque)) {
printf("Дек заполнен\r\n");
return;
}
// Вычислить указатель хвоста, указывающий на индекс хвоста + 1
int rear = dequeIndex(deque, deque->front + deque->queSize);
// Добавить num в хвост очереди
deque->nums[rear] = num;
deque->queSize++;
}
/* Доступ к элементу в начале очереди */
int peekFirst(ArrayDeque *deque) {
// Ошибка доступа: двусторонняя очередь пуста
assert(empty(deque) == 0);
return deque->nums[deque->front];
}
/* Доступ к элементу в конце очереди */
int peekLast(ArrayDeque *deque) {
// Ошибка доступа: двусторонняя очередь пуста
assert(empty(deque) == 0);
int last = dequeIndex(deque, deque->front + deque->queSize - 1);
return deque->nums[last];
}
/* Извлечение из головы очереди */
int popFirst(ArrayDeque *deque) {
int num = peekFirst(deque);
// Указатель головы сдвигается на одну позицию назад
deque->front = dequeIndex(deque, deque->front + 1);
deque->queSize--;
return num;
}
/* Извлечение из хвоста очереди */
int popLast(ArrayDeque *deque) {
int num = peekLast(deque);
deque->queSize--;
return num;
}
/* Вернуть массив для вывода */
int *toArray(ArrayDeque *deque, int *queSize) {
*queSize = deque->queSize;
int *res = (int *)calloc(deque->queSize, sizeof(int));
int j = deque->front;
for (int i = 0; i < deque->queSize; i++) {
res[i] = deque->nums[j % deque->queCapacity];
j++;
}
return res;
}
/* Driver Code */
int main() {
/* Инициализация очереди */
int capacity = 10;
int queSize;
ArrayDeque *deque = newArrayDeque(capacity);
pushLast(deque, 3);
pushLast(deque, 2);
pushLast(deque, 5);
printf("Дек deque = ");
printArray(toArray(deque, &queSize), queSize);
/* Доступ к элементу */
int peekFirstNum = peekFirst(deque);
printf("Элемент в голове peekFirst = %d\r\n", peekFirstNum);
int peekLastNum = peekLast(deque);
printf("Элемент в хвосте peekLast = %d\r\n", peekLastNum);
/* Добавление элемента в очередь */
pushLast(deque, 4);
printf("После вставки элемента 4 в хвост дек = ");
printArray(toArray(deque, &queSize), queSize);
pushFirst(deque, 1);
printf("После вставки элемента 1 в голову дек = ");
printArray(toArray(deque, &queSize), queSize);
/* Извлечение элемента из очереди */
int popLastNum = popLast(deque);
printf("Извлечен элемент из хвоста = %d, дек после извлечения из хвоста = ", popLastNum);
printArray(toArray(deque, &queSize), queSize);
int popFirstNum = popFirst(deque);
printf("Извлечен элемент из головы = %d, дек после извлечения из головы = ", popFirstNum);
printArray(toArray(deque, &queSize), queSize);
/* Получение длины очереди */
int dequeSize = size(deque);
printf("Длина дека size = %d\r\n", dequeSize);
/* Проверка, пуста ли очередь */
bool isEmpty = empty(deque);
printf("Пуста ли очередь = %s\r\n", isEmpty ? "true" : "false");
// Освободить память
delArrayDeque(deque);
return 0;
}