EE屌丝的数据结构笔记(三)

最近在笔记更新上有所懈怠,不过最终总算是没有烂尾,今天贴上前天写的一个中缀转后缀表达式的应用,顺带复习了栈和字符串的相关知识。

《计算机组成与结构》中的写到,堆栈作为一种特殊的存储结构,有着先进后出,后进先出的特点,而程序中的栈也是同样的特点,相信大多数已经学习过数据结构的人都已经非常了解栈了,我在前面顺序表的逆置中也使用了栈,前几个天写了一个中缀转后缀表达式的小程序,在此写下一些笔记心得。

首先,中缀表达式就是我们的平时常用的运算表达方法,如”3+9-2+(3*6)/2”,可见每个运算符处于两个操作数中间,而如果将以上式子转换为后缀表达式,则为”3 9 + 2 -3 6 * 2 / +”,这个过程是一个经典的栈应用,原理如下

                                          

首先转换规则为遇见数字就输出,遇见第一个符号先入栈,遇到第二个符号时,与栈顶的符号比较优先级,如果优先级相同或者新符号优先级小于栈顶符号优先级,则栈顶符号出栈输出,当前符号入栈,若优先级大于栈顶符号,则当前符号入栈。如果遇见’(‘,那么在读取时遇见’)’以后,输出’(’以后的所有入栈符号,同时将括号丢弃。当读取的式子读取完毕后,栈中仍然有符号,则一次输出至已经生成的后缀表达式末尾。

过程图解:


源代码:

acctstack.h

#ifndef ACCTSTACK_H_
#define ACCTSTACK_H_

template <class Elem>
class Stack
{
	public:
		virtual void clear() = 0;
		
		virtual bool push(const Elem &item) = 0; 
		
		virtual Elem pop() = 0;
		
		virtual Elem topValue() const = 0 ;
		
		virtual int length() const = 0;
};


#endif

stack._array.h

#include"acctstack.h"
#include<iostream>
template <class Elem>
class AStack : public Stack<Elem>
{
	private:
		int    top;
		int    size;
		Elem   *listArray;
	
	public:
		AStack(int sz)
		{
			size = sz;
			top = 0;
			listArray = new Elem[sz];
		}
		
		~AStack()
		{
			delete [] listArray;
		}
		
		void clear()
		{
			top = 0;
		}
		
		bool push(const Elem& item);
		
		Elem pop();
		
		Elem topValue() const;
		
		int length() const
		{
			return top;
		}
};

template <class Elem>
bool AStack<Elem> :: push(const Elem& item)
{
	if( top == size ){
		return false;
	}else{
		listArray[top++] = item;
		return true;
	}
}

template <class Elem>
Elem AStack<Elem> :: pop()
{
	if( top == 0 ){
		return NULL;
	}else{
		return listArray[--top] ;
	}
}

template <class Elem>
Elem AStack<Elem> :: topValue() const
{
	if( top == 0 ){
		return NULL;
	}else{
		return listArray[top - 1] ;
		
	}
}

在写栈的声明函数的时候,终于一改往常的坏习惯,避免写了太多的内联函数,以规范代码。

middle-_to_back.cpp

#include<iostream>
#include"stack_array.h"
using namespace std;

int priority(char c);

int main()
{
	cout << "Pleaer enter the funcation you want to change" 
		 << endl;
	char c[20];
	char c2[20];
	cin >> c ;
	AStack<char> Fun(100);
	int i = 0,j = 0;
	while( c[i] != '\0')
	{
		if( c[i] >= '0' && c[i] <= '9')
		{
			c2[j++] = c[i];
		} 
		
		else if( c[i] == '(')
		{
			Fun.push(c[i]);
		}
		else if( c[i] == ')')
		{
			while(Fun.topValue() != '(' )
			{
				c2[j++] = ' '; //加入空格符方便输入两位数与美观性
				c2[j++]=Fun.pop();
				
			}
			Fun.pop();
		}
		
		else if( c[i] == '+'|| c[i] == '-' ||
			c[i] == '*'|| c[i] == '/')
		{
			c2[j++] = ' ';
			while(priority(c[i]) <= priority(Fun.topValue()))
			{
			      c2[j++]=Fun.pop();
			      c2[j++] = ' ';
			}
            Fun.push(c[i]);			
		    
		}
		 i++;
	}
		
	
	
	while( Fun.length() != 0 )
	{
		c2[j++] = ' ';
		c2[j++] = Fun.pop();
	}
	
	c2[j] = '\0' ;
	cout << "Function after change is "<<endl;
	cout << c2;
};

int priority(char c) //符号优先级判断函数
{
	int priority = -1 ;
	switch(c)
	{
		case '(' : 
		case ')' : break;
		case '+' : priority = 1; break;
		case '-' : priority = 1; break;
		case '*' : priority = 2; break;
		case '/' : priority = 2; break; 
	}
	return priority ;
};

测试

测试结果成功,其中对两位数的判断也达到了设计要求(实际上多位数亦可识别,但没有加入识别小数的功能)。这次实现过程中,仍然有些问题比如栈函数pop的原型本为pop(Elem & it),但在实现过程中却无法取出出战的元素,从而修改了pop函数以适应该程序,这个问题需是要继续改进,处理字符串时使用的字符指针也出现了问题,改用了字符数组,因而这一片内容是需要再复习的。今天就写到这吧,OpenGL还有的看呢~


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
YOLO高分设计资源源码,详情请查看资源内容中使用说明 YOLO高分设计资源源码,详情请查看资源内容中使用说明 YOLO高分设计资源源码,详情请查看资源内容中使用说明 YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明YOLO高分设计资源源码,详情请查看资源内容中使用说明

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值