顺序栈的实现(ANSI C)

本文详细介绍了顺序栈的数据结构定义及其实现方法。包括初始化、清除、释放栈内存等基本操作,以及获取栈顶元素、压栈、弹栈等功能实现。通过具体的代码示例展示了如何使用顺序栈。

1、顺序栈ADT定义

#ifndef _seq_stack_h
#define _seq_stack_h

#define STACK_INIT_SIZE 100
#define STACK_INCR_SIZE 10

typedef struct seq_stack
{
	int * base;
	int * top;
	int size;
}seq_stack;

void init_stack_sq( seq_stack * ss );
void clear_stack_sq( seq_stack * ss );
void free_stack_sq( seq_stack * ss );

int stack_size_sq( seq_stack * ss );
int is_stack_empty_sq( seq_stack * ss );

int get_top_sq( seq_stack * ss, int * e );
int push_sq( seq_stack * ss, int e );
int pop_sq( seq_stack * ss, int * e );

void traverse_stack_sq( seq_stack * ss );

#endif

2、实现

#include "seq_stack.h"

#include <stdlib.h>
#include <stdio.h>
#include <assert.h>

void init_stack_sq( seq_stack * ss )
{
	ss->size = STACK_INIT_SIZE;
	ss->top = ss->base = ( int * )malloc( sizeof( int ) * ss->size );
	assert( ss->base != NULL );
}

void clear_stack_sq( seq_stack * ss )
{
	assert( ss != NULL );
	ss->top = ss->base;
}

void free_stack_sq( seq_stack * ss )
{
	assert( ss != NULL && ss->base != NULL );
	ss->size = 0;
	free( ss->base );
	ss->base = ss->top = NULL;
}

int stack_size_sq( seq_stack * ss )
{
	assert( ss != NULL );
	return ss->size;
}

int is_stack_empty_sq( seq_stack * ss )
{
	assert( ss != NULL && ss->base != NULL );
	return ss->base == ss->top;
}

void traverse_stack_sq(  seq_stack * ss )
{
	int * p = NULL;
	assert( ss != NULL && ss->base != NULL );
	for( p = ss->base; p < ss->top; ++p )
		printf( "%d ", *p );
	putchar( '\n' );
}

int get_top_sq(  seq_stack * ss, int * e )
{
	assert( ss != NULL && ss->base != NULL );
	if( ss->base == ss->top )
		return -1;

	*e = *( ss->top - 1 );
	return 1;
}

int is_stack_full_sq( seq_stack * ss )
{
	return ss->base + ss->size == ss->top;
}

void expand_stack( seq_stack * ss )
{
	int * new_base = NULL, i;
	new_base = ( int * )malloc( sizeof( int ) * ( ss->size + STACK_INCR_SIZE ) );
	assert( new_base != NULL );
	for( i = 0; i < ss->size; ++i )
		new_base[i] = ss->base[i];
	free( ss->base );
	ss->base = new_base;
	ss->top = ss->base + ss->size;
	ss->size += STACK_INCR_SIZE;
}

int push_sq( seq_stack * ss, int e )
{
	assert( ss != NULL && ss->base != NULL );

	if( is_stack_full_sq( ss ) )
		expand_stack( ss );

	*ss->top++ = e;
	return 1;
}

int pop_sq( seq_stack * ss, int * e )
{
	assert( ss != NULL && ss->base != NULL );
	if( ss->base == ss->top )
		return -1;
	*e = *--ss->top;
	return 1;
}
//顺序栈基本运算算法 #include <stdio.h> #include <malloc.h> #define MaxSize 100 typedef char ElemType; typedef struct { ElemType data[MaxSize]; int top; //栈指针 } SqStack; //顺序栈类型 void InitStack(SqStack * &s){ s=(SqStack *)malloc(sizeof(SqStack)); s->top=-1; } bool pdtrue(){ return true; } bool StackEmpty_1(SqStack * s) { return s->top==-1; } void StackEmpty(SqStack * s) { if(s->top==-1){ printf("顺序栈为空\n"); } else{ printf("顺序栈不为空\n"); } } void main(){ SqStack *s=NULL; InitStack(s); printf("顺序表地址为%p\n",s); bool as; as=pdtrue(); if(as==true) { printf("as的值为true"); } StackEmpty(s); } 实验三 实验报告 2025 – 2026 学年度第 1 学期 任课教师: 杜 峰 云 课程名称 数据结构与算法 班级 学号 姓名 实验题目 栈的基本操作 实验时间 实验开始日期:2025年 月 日 实验提交日期:2025年 月 日 实验目的 一、目的在于通过实践加深对顺序栈这一数据结构的理解与应用能力,理解顺序栈的定义、存储结构(基于数组的顺序存储特性)及 “后进先出(LIFO)” 的核心特性,明确栈顶指针在顺序栈操作中的关键作用,掌握初始化、判空、入栈、出栈、取栈顶元素、销毁等操作的底层逻辑。 二、掌握实操技能:熟练运用编程语言(如 C/C++ 等)实现顺序栈的六大基本操作: 1)掌握顺序栈初始化的实现方法,能正确构建栈的存储结构(如初始化数组、设置栈顶指针初始值等); 2)理解并实现 “判断栈是否为空” 的逻辑(通过栈顶指针状态判断); 3)掌握入栈操作的实现,包括元素插入到栈顶的步骤,以及栈满时的边界处理; 4)掌握出栈操作的实现,包括移除栈顶元素的步骤,以及栈空时的异常处理; 5)学会通过栈顶指针获取栈顶元素,理解该操作 “不改变栈状态” 的特性; 6)掌握销毁顺序栈的方法,正确释放栈所占用的内存资源,避免内存泄漏。 三、培养综合能力:通过代码编写、调试与优化,提升将数据结构理论转化为实际程序的能力,强化对 “顺序存储” 中内存管理、边界条件处理的意识,为后续学习更复杂的数据结构(如链栈、队列、树等)及算法应用奠定基础。 实验环境概述 本实验所使用的开发环境为 Microsoft Visual C++ 2010 Express(简称 VS2010 Express),它是微软公司推出的一款轻量级集成开发环境(IDE),主要用于 C 语言和 C++ 语言的程序开发。 1. 开发环境配置 VS2010 Express 运行于 Windows 操作系统(兼容 Windows 7、Windows 10 等常见版本),集成了代码编辑器、编译器、链接器与调试器等工具,为 C/C++ 程序开发提供了 “编写 - 编译 - 调试 - 运行” 的一体化流程支持,便于开发者高效完成代码的创建、修改与验证。 2. 编译器与语言支持 该环境内置的 C/C++ 编译器支持 ANSI C 标准(如 C89、C99 等)与 C++ 标准(如 C++98 等),可将 C/C++ 源代码转换为可执行的机器代码。编译阶段会对代码进行语法检查、逻辑分析与性能优化,保障程序的正确性与运行效率。 3. 程序运行环境 通过 VS2010 Express 编译生成的可执行文件(.exe 格式),可直接在 Windows 操作系统下独立运行,无需依赖开发环境本身,便于程序的分发与测试验证。 实验内容 已知顺序表结构与相关函数定义如书本所示,基于书中程序完成下列题目 输入头文件和预处理指令 //顺序栈基本运算算法 #include <stdio.h> #include <malloc.h> #define MaxSize 100 typedef char ElemType; typedef struct { ElemType data[MaxSize]; int top; //栈指针 } SqStack; //顺序栈类型 ①创建顺序栈SqStack:基于书本代码创建顺序栈结构体 代码截图: ②顺序栈的初始化InitStack:完成栈的初始化程序InitStack,并在主函数中创建一个空指针L(授课过程中讲的:结构体名字 * 指针名;并赋初始值NULL。SqStack * S = NULL;),调用初始化顺序栈函数(调用方式:函数名(参数),例如:InitStack(S)),让指针S指向初始化的顺序栈,最终使用printf输出初始化后的顺序表的地址(输出方式printf(“顺序表地址为%p\n”,L)。 %p是C语言中输出变量的方式,此时的%p就等于我们后面的变量L,\n代表换行。 %d输出的是数字,%c输出的是字母 代码截图: 运行结果截图: ③判断顺序栈是否为空StackEmpty:判断指针指向位置是否为-1,若为则输出栈空,否则。 代码截图: 运行结果截图: ④入栈Push:入栈操作需要先判断顺序栈是否已满(s->top == MAXSIZE-1);需要先自增指针top,让指针指向栈中的下一个位置;将传递进来的参数(函数调用时传进来的参数ElemType e)赋值给顺序栈中data里的指针位置(s->data[s->top])。 代码截图: 运行结果截图: ⑤出栈Pop:出栈操作前需要先判断顺序栈是否为空(S->top == -1);若需要保存出栈的值,则在一开始需要在函数体内接收传递参数的地址(bool Pop(SqStack * &S,ElementType &e),&符号的作用是获取变量e的存储地址,这样能够在函数体内修改变量e的值);若不需要保存,则指针s->top--自减1,栈顶下移。 代码截图: 运行结果截图: ⑥按顺序输出整个顺序栈:整个程序由循环和输出两个部分组成。输出部分由print函数组成,输出顺序栈S中data里的top位(s->data[s->top]),输出完成后自减top值;使用while循环依次递减top的值,直到top小于0 代码截图: 运行结果截图: ⑦销毁顺序栈:传递顺序栈指针,使用free函数释放指针指向的地址 代码截图: 运行结果截图: 提高性项目:基于栈的特性,实现十进制转八进制的代码实现。 步骤: ①定义顺序栈 ②使用辗转相除法将该十进制数除以八,将余数依次入栈 ③将栈中元素依次出栈 ④销毁顺序栈 实验发现的问题与处理描述 实验总结以及新的体会
最新发布
10-22
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值