📜  堆栈实现 - C++ (1)

📅  最后修改于: 2023-12-03 14:51:37.821000             🧑  作者: Mango

堆栈实现 - C++

什么是堆栈

堆栈是一种线性数据结构,它只允许在一端进行插入和删除操作,这一端被称为栈顶,另一端被称为栈底。栈的特点是后进先出,即最后放入的元素最先弹出,而最先放入的元素最后弹出。

如何使用C++实现堆栈

我们可以使用C++中的数组或链表来实现堆栈。对于数组实现,我们需要提前确定一个最大的存储空间,而链表则可以根据需要动态分配空间。

数组实现

我们可以使用一个数组来模拟一个固定大小的堆栈。我们需要使用一个指针来指向栈顶元素的位置。

#define MAX_SIZE 100 // 定义栈的最大大小

class Stack {
private:
    int data[MAX_SIZE]; // 数组用于存储元素
    int top; // 指针指向栈顶的位置

public:
    Stack() { top = -1; } // 初始化栈,使栈顶指针指向-1,表示栈为空

    bool push(int x) {
        if (top >= MAX_SIZE - 1) { // 如果栈满了,无法进行入栈操作
            return false;
        }
        data[++top] = x; // 将新元素入栈,并将栈顶指针指向新元素位置
        return true;
    }

    int pop() {
        if (top == -1) { // 如果栈为空,无法进行出栈操作
            return INT_MAX; // 返回最大整数(这里只是一个示范,在实际中需要根据实际情况返回合适的值,例如抛出一个异常)
        }
        return data[top--]; // 弹出栈顶元素,并将栈顶指针指向它的下一个位置
    }

    int peek() { // 返回栈顶元素的值
        if (top == -1) {
            return INT_MAX; // 返回最大整数
        }
        return data[top];
    }

    bool isEmpty() { // 判断栈是否为空
        return top == -1;
    }
};
链表实现

链表实现堆栈可以动态分配内存,不需要预先确定最大的存储空间。我们可以将新元素插入到链表的头部,将栈顶指针指向新元素。

class StackNode {
public:
    int val;
    StackNode* next;
    StackNode(int value) : val(value), next(nullptr) {}
};

class Stack {
private:
    StackNode* top;

public:
    Stack() { top = nullptr; }

    void push(int x) {
        StackNode* node = new StackNode(x); // 创建新节点
        node->next = top; // 新节点的下一个节点是当前栈顶节点
        top = node; // 更新栈顶节点
    }

    int pop() { // 弹出栈顶节点
        if (top == nullptr) {
            return INT_MAX;
        }
        StackNode* tmp = top; // 保存当前栈顶节点指针
        int ret = tmp->val; // 保存当前栈顶节点的值
        top = top->next; // 更新栈顶节点指针
        delete tmp; // 删除已经弹出的节点
        return ret;
    }

    int peek() { // 返回栈顶元素的值
        if (top == nullptr) {
            return INT_MAX;
        }
        return top->val;
    }

    bool isEmpty() { // 判断栈是否为空
        return top == nullptr;
    }
};
总结

无论使用数组还是链表实现堆栈,我们都需要注意以下几点:

  • 确定栈的最大大小或不预先确定大小
  • 确定栈顶指针的初始位置
  • 实现push、pop、peek和isEmpty方法
  • 处理栈满或栈空的情况