一、顺序栈类型的定义
#include <stdio.h>
#include <malloc.h>
#include <stdlib.h>
#define STACK_INIT_SIZE 10
#define STACKINCREMENT 2
typedef int INT;
typedef bool BOOL;
typedef struct stack {
INT *base;
INT *top;
INT stacksize;
};
enum STATUS {ERROR = -1, OK = 0};
STATUS InitStack(stack &s)
{
if (NULL == (s.base = (INT *)malloc(STACK_INIT_SIZE * sizeof(INT)))) {
exit(-1);
}
s.top = s.base;
s.stacksize = STACK_INIT_SIZE;
return OK;
}
STATUS DestroyStack(stack &s)
{
free(s.base);
s.base = NULL;
s.top = NULL;
s.stacksize = 0;
return OK;
}
STATUS ClearStack(stack &s)
{
s.top = s.base;
return OK;
}
BOOL IsEmpty(stack s)
{
if (s.top == s.base) {
return true;
} else {
return false;
}
}
INT GetLength(stack s)
{
return s.top - s.base;
}
STATUS GetTop(stack s, INT &e)
{
if (s.top > s.base) {
e = *(s.top - 1);
return OK;
} else {
return ERROR;
}
}
STATUS Push(stack &s, INT e)
{
if (s.top - s.base >= s.stacksize) {
if (NULL == (s.base = (INT *)realloc(s.base, sizeof(INT) * (s.stacksize + STACKINCREMENT)))) {
exit(-1);
}
s.top = s.base + s.stacksize;
s.stacksize += STACKINCREMENT;
}
*(s.top ++) = e;
return OK;
}
STATUS Pop(stack &s, INT &e)
{
if (s.top > s.base) {
e = *(-- s.top);
return OK;
} else {
return ERROR;
}
}
STATUS TraverseStack(stack s, STATUS (*visit)( INT ))
{
while (s.top > s.base){
visit(*s.base ++);
}
printf("\n");
return OK;
}
STATUS PrintElement(INT e)
{
printf("Element : %d\n", e);
return OK;
}
int main(int argc, char **argv)
{
int i,j,k;
stack s;
InitStack(s);
for(i = 0; i < 100; ++ i) {
Push(s,i);
}
int e;
j = GetTop(s,e);
printf("j = %d, Top Element : %d\n", j, e);
printf("Lenght = %d\n", GetLength(s));
typedef STATUS (*PTRFUN)( INT );
PTRFUN func = PrintElement;
TraverseStack(s, func);
return 0;
}
// c3-1.h 栈的顺序存储表示
#define STACK_INIT_SIZE 10 // 存储空间初始分配量
#define STACKINCREMENT 2 // 存储空间分配增量
struct SqStack
{
SElemType *base; // 在栈构造之前和销毁之后,base的值为NULL
SElemType *top; // 栈顶指针
int stacksize; // 当前已分配的存储空间,以元素为单位
}; // 顺序栈
// bo3-1.cpp 顺序栈(存储结构由c3-1.h定义)的基本操作(9个)
Status InitStack(SqStack &S)
{ // 构造一个空栈S
if(!(S.base=(SElemType *)malloc(STACK_INIT_SIZE*sizeof(SElemType))))
exit(OVERFLOW); // 存储分配失败
S.top=S.base;
S.stacksize=STACK_INIT_SIZE;
return OK;
}
Status DestroyStack(SqStack &S)
{ // 销毁栈S,S不再存在
free(S.base);
S.base=NULL;
S.top=NULL;
S.stacksize=0;
return OK;
}
Status ClearStack(SqStack &S)
{ // 把S置为空栈
S.top=S.base;
return OK;
}
Status StackEmpty(SqStack S)
{ // 若栈S为空栈,则返回TRUE,否则返回FALSE
if(S.top==S.base)
return TRUE;
else
return FALSE;
}
int StackLength(SqStack S)
{ // 返回S的元素个数,即栈的长度
return S.top-S.base;
}
Status GetTop(SqStack S,SElemType &e)
{ // 若栈不空,则用e返回S的栈顶元素,并返回OK;否则返回ERROR
if(S.top>S.base)
{
e=*(S.top-1);
return OK;
}
else
return ERROR;
}
Status Push(SqStack &S,SElemType e)
{ // 插入元素e为新的栈顶元素
if(S.top-S.base>=S.stacksize) // 栈满,追加存储空间
{
S.base=(SElemType *)realloc(S.base,(S.stacksize+STACKINCREMENT)*sizeof(SElemType));
if(!S.base)
exit(OVERFLOW); // 存储分配失败
S.top=S.base+S.stacksize;
S.stacksize+=STACKINCREMENT;
}
*(S.top)++=e;
return OK;
}
Status Pop(SqStack &S,SElemType &e)
{ // 若栈不空,则删除S的栈顶元素,用e返回其值,并返回OK;否则返回ERROR
if(S.top==S.base)
return ERROR;
e=*--S.top;
return OK;
}
Status StackTraverse(SqStack S,Status(*visit)(SElemType))
{ // 从栈底到栈顶依次对栈中每个元素调用函数visit()。
// 一旦visit()失败,则操作失败
while(S.top>S.base)
visit(*S.base++);
printf("\n");
return OK;
}
实例应用:
// algo3-1.cpp 调用算法3.1的程序
typedef int SElemType; // 定义栈元素类型为整型
#include"c1.h"
#include"c3-1.h" // 采用顺序栈
#include"bo3-1.cpp" // 利用顺序栈的基本操作
void conversion() // 算法3.1
{ // 对于输入的任意一个非负十进制整数,打印输出与其等值的八进制数
SqStack s;
unsigned n; // 非负整数
SElemType e;
InitStack(s); // 初始化栈
printf("n(>=0)=");
scanf("%u",&n); // 输入非负十进制整数n
while(n) // 当n不等于0
{
Push(s,n%8); // 入栈n除以8的余数(8进制的低位)
n=n/8;
}
while(!StackEmpty(s)) // 当栈不空
{
Pop(s,e); // 弹出栈顶元素且赋值给e
printf("%d",e); // 输出e
}
printf("\n");
}
void main()
{
conversion();
}
// algo3-2.cpp 改算法3.1,10进制→16进制
typedef int SElemType; // 定义栈元素类型为整型
#include"c1.h"
#include"c3-1.h" // 采用顺序栈
#include"bo3-1.cpp" // 利用顺序栈的基本操作
void conversion()
{ // 对于输入的任意一个非负10进制整数,打印输出与其等值的16进制数
SqStack s;
unsigned n; // 非负整数
SElemType e;
InitStack(s); // 初始化栈
printf("n(>=0)=");
scanf("%u",&n); // 输入非负十进制整数n
while(n) // 当n不等于0
{
Push(s,n%16); // 入栈n除以16的余数(16进制的低位)
n=n/16;
}
while(!StackEmpty(s)) // 当栈不空
{
Pop(s,e); // 弹出栈顶元素且赋值给e
if(e<=9)
printf("%d",e);
else
printf("%c",e+55);
}
printf("\n");
}
void main()
{
conversion();
}
void check()
{ // 对于输入的任意一个字符串,检验括号是否配对
SqStack s;
SElemType ch[80],*p,e;
if(InitStack(s)) // 初始化栈成功
{
printf("请输入表达式\n");
gets(ch);
p=ch;
while(*p) // 没到串尾
switch(*p)
{
case '(':
case '[':Push(s,*p++);
break; // 左括号入栈,且p++
case ')':
case ']':if(!StackEmpty(s)) // 栈不空
{
Pop(s,e); // 弹出栈顶元素
if(*p==')'&&e!='('||*p==']'&&e!='[') // 弹出的栈顶元素与*p不配对
{
printf("左右括号不配对\n");
exit(ERROR);
}
else
{
p++;
break; // 跳出switch语句
}
}
else // 栈空
{
printf("缺乏左括号\n");
exit(ERROR);
}
default: p++; // 其它字符不处理,指针向后移
}
if(StackEmpty(s)) // 字符串结束时栈空
printf("括号匹配\n");
else
printf("缺乏右括号\n");
}
}
二、C++实现栈
/***************************************************************************
*
* Copyright (c) 2015 Baidu.com, Inc. All Rights Reserved
*
**************************************************************************/
/**
* @file stack.h
* @author tianmo(com@baidu.com)
* @date 2015/04/21 23:43:25
* @brief
*
**/
#ifndef __STACK_H_
#define __STACK_H_
#include <iostream>
#include <stdlib.h>
template <class _Tp>
class stack {
public:
typedef _Tp value_type;
typedef int value_size;
public:
stack() {
_base = new (std::nothrow) value_type[MAX_SIZE];
if (_base == NULL) {
std::cout<<"fail to allocate stack memory";
exit(-1);
}
_top = _base;
_max_size = MAX_SIZE;
}
stack(const value_size& max_size) {
_base = new (std::nothrow) value_type[max_size];
if (_base == NULL) {
std::cout<<"fail to allocate stack memory";
exit(-1);
}
_top = _base;
_max_size = max_size;
}
~stack() {
if (_base != NULL) {
delete []_base;
_base = NULL;
_top = NULL;
_max_size = 0;
}
}
bool is_full() {
return _top - _base >= _max_size;
}
bool is_empty() {
return _top == _base;
}
bool push(const value_type& item) {
if (is_full()) {
_base = (value_type*)realloc(_base, sizeof(value_type) * (_max_size + INCREMENT_SIZE));
if (_base == NULL) {
return false;
}
_top = _base + _max_size;
_max_size += INCREMENT_SIZE;
}
*_top = item;
++_top;
return true;
}
bool pop(value_type* item) {
if (is_empty()) {
return false;
}
--_top;
*item = *_top;
return true;
}
bool top(value_type* item) {
if (is_empty()) {
return false;
}
*item = *(_top - 1);
return true;
}
value_size size() const {
return _top - _base;
}
private:
// 始终指向栈底的指针
value_type *_base;
// 始终指向栈顶的指针
value_type *_top;
// 栈当前的最大容量
value_size _max_size;
// 栈当前的最大容量
const static value_size MAX_SIZE = 1000;
// 栈满后,每次增加的容量
const static value_size INCREMENT_SIZE = 100;
};
#endif //__STACK_H_
/* vim: set expandtab ts=4 sw=4 sts=4 tw=100: */
/***************************************************************************
*
* Copyright (c) 2015 Baidu.com, Inc. All Rights Reserved
*
**************************************************************************/
/**
* @file demo.cc
* @author tianmo(com@baidu.com)
* @date 2015/04/21 23:59:50
* @brief
*
**/
#include <stdio.h>
#include "stack.h"
int main() {
stack<int> s(101);
for (int i = 0; i < 10000; ++i) {
s.push(i);
}
int size = s.size();
printf("stack[%d] is full ? %s\n", size, s.is_full() ? "yes" : "no");
/*
for (int i = 0; i < size; ++i) {
int temp;
if (s.pop(&temp)) {
printf("%d ", temp);
}
}
*/
int top;
if (s.top(&top)) {
printf("stack top:%d\n", top);
}
return 0;
}
/* vim: set expandtab ts=4 sw=4 sts=4 tw=100: */