本篇我们就讨论一个问题:如何用数组实现栈?
1.构建结构体
struct Stack {
int* items;
int top;
int capacity;
};
其中items
指向数组的指针,top
代表的是栈顶元素的索引,capacity
用于记录数组初始化的大小,到时候可以用于判断栈是否满了。
2.初始化栈
Stack* create_stack(int capacity) {
//创建一个栈
Stack* stack = new Stack();
stack->items = new int[capacity];
stack->top = -1;
stack->capacity = capacity;
return stack;
}
stack->items = new int[capacity];
的意思是根据你穿来的大小capacity
创建一个capacity
大小的数组,把数组的首地址保存在stack
本身的items
的指针上,方便以后访问。这个方法返回一个指向栈的指针,可以通过指针来访问栈。
3.判断栈是否为空
bool is_empty01(Stack* stack) {
return stack->top == -1;
}
注意:vs中这里不能命名为is_empty好像是系统内置了一个is_empty。
4.判断栈是否为满
bool is_full(Stack* stack) {
return stack->top == stack->capacity - 1;
}
5.入栈
void push(Stack* stack, int item) {
if (is_full(stack)) {
cout << "栈已经满了" << endl;
return;
}
stack->items[++stack->top] = item;
}
stack->top
表示栈顶元素的索引。
++stack->top
会先将stack->top
的值加1,然后返回增加后的值。也就是说,这行代码将栈顶索引自增,使其指向新的空闲位置。stack->items
是一个指向整型数组的指针,表示存储栈元素的数组。stack->items[++stack->top]
表示通过栈顶索引找到下一个空闲位置,然后将其赋值为item
。
6.出栈
int pop(Stack* stack) {
if (is_empty01(stack)) {
cout << "这个栈已经空了" << endl;
return 0;
}
return stack->items[stack->top--];
}
根据stack->top
返回数组中的元素,然后stack->top--
,栈顶元素改变。
7.返回栈顶元素
int peek(Stack* stack) {
if (is_empty01(stack)) {
cout << "这个栈已经空了" << endl;
return 0;
}
return stack->items[stack->top];
}
返回顶部元素,但是不会取出来,只是看看,栈顶元素不会变。
8.返回栈的大小
int size01(Stack* stack) {
return stack->top+1;
}
这里在vs中同样不能定义size,似乎是因为系统内置了一个同名的。
9.测试用例
int main() {
//创建一个容量为100的栈
Stack* stack = create_stack(100);
//入栈
push(stack, 1);
push(stack, 2);
push(stack, 3);
//返回栈顶元素
int a = peek(stack);
cout << a << endl;
//出栈
pop(stack);
int size = size01(stack);
cout << size << endl;
}
最后输出两个数字:3,2。