栈和队列

顺序栈

#include<stdio.h>
#include<stdlib.h>
#define MAXSIZE 30 
typedef int ElemType;  
//顺序栈的结构定义
typedef struct{
	ElemType data[MAXSIZE];  //数组
	int top;
}SeqStack;

//栈的初始化
 SeqStack *InitStack(){
 	SeqStack *s;
 	s=(SeqStack*)malloc(sizeof(SeqStack)); 
 	s->top=-1;//top定在-1      //如果是0的话,表示索引到零号元素 
	return s;
 }
 
 //判空栈
 //返回1表示是空栈 , 返回0表示不是空栈
 int Empty(SeqStack *s){
 	if(s->top==-1)
	 return 1;
	 else
	 return 0;
 }
  
 //入栈(push)
 //将元素x压入栈中
 //返回0表示栈满 , 返回1表示入栈成功
 int Push(SeqStack *s,ElemType x){     //传入的参数是一个指向栈的结构体指针和一个要存入栈顶的元素 
 	if(s->top==MAXSIZE-1){ 
 		return 0;
	 }else{
	 	s->top++;
	 	s->data[s->top]=x;   //[s->top]是指数组的第几个元素 
	 	return 1;
	 }
 }
 
 //出栈 (popup)
 //注意此时的参数需要带*,需要对调用地址操作
 //返回0表示空栈了,返回1表示出栈成功 
 int Pop(SeqStack* s,ElemType *x){
 	if(s->top==-1){
 		return 0;
	 }else{
	 	*x=s->data[s->top];
		 s->top--;
		 return 1; 
	 }
 }
 
 //取出栈顶元素
 //返回0表示当前栈为空栈,否则返回栈顶元素的值 
 ElemType GetTop(SeqStack* s){
 	if(s->top==-1){
 		return 0;
	 }else{
	 	return (s->data[s->top]);
	 }
 } 
 
  
int main(){
	SeqStack* s=InitStack();//初始化栈
	printf("%d\n",Push(s,3));
	printf("%d\n",Push(s,4));
	printf("%d\n",GetTop(s));
	int i;
	printf("%d\n",Pop(s,&i));  //在函数中对i赋值改变,因为传递的是地址,所以函数中赋值改变后在主函数中依然起作用 
	printf("%d",i);
//	printf("%d\n",GetTop(s));
//	printf("%d\n",Empty(s));
//	printf("%d\n",Pop(s,&i));
//	printf("%d\n",Empty(s));
}

须注意的地方都已在代码中注释出

链栈

#include<stdio.h>
#include<stdlib.h>
typedef int ElemType;

//链栈的结构定义
//每个结点 
typedef struct StackNode{
	ElemType data;
	struct StackNode *next;
}StackNode,*LinkStackPtr;  //pointer指针   stack栈;堆栈   linked list 链表 
//结构体变量,结构体指针变量 
 
//top结构体
typedef struct{
   LinkStackPtr top;  //结构体指针 
   //int count;//记录线性表的长度
}LinkStack;
//结构体变量

//栈的初始化
LinkStack* InitStack(){
	LinkStack* s;
	s=(LinkStack *)malloc(sizeof(LinkStack));
	//s->count=0;
	s->top=NULL;
	return s;
}

//判空栈
int Empty(LinkStack *s){
	if(s->top==NULL){
		return 1;
		//返回1表示空栈
	}else{
		return 0;
		//返回0表示不为空栈
	} 
}

//入栈
int Push(LinkStack *s,ElemType x){
	LinkStackPtr p;  //结构体指针 
	if((p=(LinkStackPtr)malloc(sizeof(StackNode)))==NULL){   //申请的空间是第一个结构体大小的一块空间 
		return 0;
		//返回0表示无内存空间了 
	}
	p->data=x;  
	p->next=s->top;   //p的next指向原来的栈顶top   (top和p是同类型的结构体数据,因此可以进行整体赋值操作)(top不仅仅只是一个指针) 
	s->top=p;  //栈顶top指向新节点p
	return 1;
	//返回1表示入栈成功 
} 

//出栈
int Pop(LinkStack *s,ElemType *x){
	LinkStackPtr p;  //定义一个结构体指针 
if(Empty(s)){
	return 0;
	//返回0表示此栈为空栈
    }else{
	p=s->top;//p指针和top指针指向同一块地址 , 即此时栈顶的地址 
	*x=p->data; //将栈顶元素中的数据赋给指针x 
	s->top=p->next;//将栈顶指向下一个 
	free(p);//将p,即原来的栈顶free掉 
	return 1;
	//返回1表示出栈成功 
  } 
} 

//取出栈顶元素
 ElemType GetTop(LinkStack* s){
 	if(s->top==NULL){
 		return 0;
 		//返回0表示空栈了 
	 }else{
	   return s->top->data;// 
	} 
 } 
 
int main(){
	LinkStack* s=InitStack();
	Push(s,4);
	Push(s,5);
	printf("%d\n",GetTop(s));
	int i;
	printf("%d\n",Pop(s,&i));
	printf("%d\n",GetTop(s));
	printf("%d\n",Empty(s));
	printf("%d\n",Pop(s,&i));
	printf("%d\n",Empty(s));
}

须注意的地方都已在代码中注释出

队列的知识点

  1. 队列定义
    队列(Queue)是一种先进先出的线性表简称FIFO(First In First Out)。允许插入的一端称为队尾,允许删除的一端称为队头。

  2. 入队列。其实就是在队尾追加一个元素,并不需要移动任何元素。

  3. 出队列。出去一个元素后,队列中的剩余其他所有元素都得向前移动,以保证队头不为空。

  4. 计算队列长度。首先定义两个指针front和rear,front指针指向队头元素,rear指针指向队尾元素的下一个位置,这样的话当front等于rear时,此队列为空队列。(队列的最大尺寸为QueueSize)
    计算长度的通式为:(rear - front + QueueSize)% QueueSize

  5. 队列基本分为顺序队列,循环队列,链队列。

  6. 循环队列需要事先申请好空间,使用期间不释放。因此必须拥有一个固定的长度,所以会有元素个数,空间的浪费。

  7. 链队列则每次申请空间,不需要了在释放掉,不会造成元素个数,空间的浪费,但每次申请释放空间也会浪费一定的时间。所以在空间上,链队列更为灵活一些。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值