问题分析

本题要求我们实现一个简单的栈结构,并实现以下基本操作:

// 初始化一个栈
void initialize(struct stack* s);
// 弹出栈顶元素,并返回该元素,如果栈为空,返回-1
int pop(struct stack* s);
// 向栈中增加元素,并返回该元素,如果栈已满,返回-1
int push(struct stack* s, int number);
// 返回栈的长度
int get_size(struct stack* s);
// 返回栈顶元素,若栈为空,返回-1
int get_top(struct stack* s);
// 判断栈是否为空,若是,返回1,否则,返回0
int empty(struct stack* s);
// 输出栈,若栈为空,输出“Empty stack”
void list(struct stack* s);

解析

栈是一种后进先出的数据结构,本质上可以用数组实现,同时需要维护一个指示栈顶位置的变量 top。

初始化

void initialize(struct stack *s)
{
    s->top = -1; // 栈顶位置指针,-1 即为空栈
    s->elements = (int *)malloc(MAX_SIZE * sizeof(int));
}

入栈出栈

int pop(struct stack *s)
{
    if (s->top > -1) // 栈不为空
    {
        s->top--;
        return s->elements[s->top + 1];
    }
    return -1;
}

int push(struct stack *s, int number)
{
    if (s->top < MAX_SIZE - 1) // 栈未满
    {
        s->top++;
        s->elements[s->top] = number;
        return number;
    }
    return -1;
}

注意若入栈成功需要返回压入的数。

判断及输出

int get_size(struct stack *s)
{
    return s->top + 1; // 下标从 0 开始,所以要加 1
}

int get_top(struct stack *s)
{
    if (s->top > -1)
        return s->elements[s->top];
    return -1;
}

int empty(struct stack *s)
{
    if (s->top == -1)
        return 1;
    return 0;
}

void list(struct stack *s)
{
    if (s->top == -1)
    {
        printf("Empty stack\n");
        return;
    }
    for (int i = s->top; i >= 0; i--) // 注意题目要求从栈顶到栈底打印
        printf("%d ", s->elements[i]);
    printf("\n");
}

要点

题解中为了便于理解,将语句分开来写了。
为提升代码的简洁性,可以利用自增/自减运算符,赋值语句的返回值,以及三目运算符等特性,将代码优化如下:

int pop(struct stack *s)
{
    if (s->top > -1)
        return s->elements[s->top--]; // 先返回栈顶元素再自减
    return -1;
}

int push(struct stack *s, int number)
{
    if (s->top < MAX_SIZE - 1)
        return s->elements[++s->top] = number;
        /* 先自增再赋值
            a = b 赋值语句的返回值为 b,所以 return a = b 返回 b。
        */
    return -1;
}

int empty(struct stack *s)
{
    return s->top == -1 ? 1 : 0;
    /* 三目运算符,等价于
        if (s->top == -1)
            return 1;
        else
            return 0;
    */
}

这些技巧在考试等限时场景下可有效节省时间。