c语言的数据结构表达式求值

article/2025/9/15 16:17:01

最近学习c语言的数据结构中有关栈的实现。下面是用栈实现表达式求值的一个实例,用的是顺序栈的形式
原理

  1. List item

我们默认一‘#’开始,最后输入’#‘结束

在运算中的每一步中,任意两个相继出现的算符theta1和theta2之间的关系,至多只有三种关系:
1,theta1<theta2
2,theta1>theta2
3,theta1=theta2
theta1和theta2之间的关系由下表给出
在这里插入图片描述

根据算数运算规则的左结合性,先压入栈的同型号运算符优先级要大些,比如栈顶为‘+’,输入为‘+’,此时该算那个‘+’呢,应该算栈顶那个‘+’;
因为我们无法比较(和#,(,#,)之间的优先级关系所以如果输入这种运算符的话程序将会出错,所以在程序中应注意避免
算法
该算法把数字和字符都以char型入栈
1)初始化opnd(数字)和optr(字符)栈,将#压入oper栈
2)循环表达式如果输入的值ch非#和栈顶元素非#则执行以下操作:
若输入的值不是运算符,则压入opnd(数字)栈
否则将输入的值与栈顶进行比较
若是<则ch压入optr栈,读入下一字符
若是>则optr弹出运算符,opnd弹出两个元素,和运算符进行运算
若是=则optr栈顶元素是(且ch是),弹出optr栈顶,相当于括号匹配成功
3)最后循环结束opnd栈顶元素即为所求值
以下是源代码,所用软件是visualstudio2022

#include<stdio.h>
#include<stdlib.h>
#include<malloc.h>
#include"pch.h"#define STACK_CHAR_SIZE 100
#define STACKINCREMENT 10typedef struct {char* base;char* top;int stacksize;
}SqStack;//获取theta所对应的索引
//返回索引值
int getIndex(char theta)   
{int index = -1;switch (theta){case '+':index = 0;break;case '-':index = 1;break;case '*':index = 2;break;case '/':index = 3;break;case '(':index = 4;break;case ')':index = 5;break;case '#':index = 6;default:break;}return index;
}
//输入索引值
//返回优先级关系
char getPriority(char theta1, char theta2)   //获取theta1与theta2之间的优先级  
{const char priority[][7] =     //算符间的优先级关系  {{ '>', '>', '<', '<', '<', '>', '>' },{ '>', '>', '<', '<', '<', '>', '>' },{ '>', '>', '>', '>', '<', '>', '>' },{ '>', '>', '>', '>', '<', '>', '>' },{ '<', '<', '<', '<', '<', '=', '0' },{ '>', '>', '>', '>', '0', '>', '>' },{ '<', '<', '<', '<', '<', '0', '=' },};int index1 = getIndex(theta1);int index2 = getIndex(theta2);return priority[index1][index2];
}//初始化栈
bool InitStack(SqStack&S)
{S.base = NULL;S.base = (char*)malloc(sizeof(char)*STACK_CHAR_SIZE);if (!S.base){return false;}S.top = S.base;S.stacksize = STACK_CHAR_SIZE;return true;}int DestoryStack(SqStack& S) {if (S.base == NULL) exit(1);free(S.base);S.base = NULL;return true;
}int ClearStack(SqStack& S)
{if (S.base == NULL)exit(1);S.top = S.base;return true;
}char GetTop(SqStack& S) {if (S.top != S.base) return *(S.top - 1);
}bool Push(SqStack& S, char e) {if (S.top - S.base == S.stacksize){return false;}*S.top++ = e;return true;
}char Pop(SqStack& S, char& e) {if (S.top == S.base) return false;e = *--S.top;return true;
}//输入操作数aa,操作符theta,操作数bb
//输出操作后结果
char Operate(char aa, char theta, char bb)
{int a = aa-'0';//将字符型数字转换成int型int b = bb-'0';int res = 0;switch (theta){case '+':res = a + b;break;case '-':res = a - b;break;case '*':res = a * b;break;case '/':res = a / b;break;default:break;}return res+'0';
}
int main()
{SqStack opnd, optr;//初始化运算符栈optr,操作数栈opndchar ch,flag2,theta,a,b,x;int flag1,res;InitStack(opnd); InitStack(optr);//初始化Push(optr, '#');printf("请输入表达式: ");scanf(" %c", &ch);//在ch不为#或者optr栈顶不为#时循环while (ch != '#'||GetTop(optr) != '#'){//如果ch为数字就插入opnd栈//判断是否为数字用的是函数getIndexflag1= getIndex(ch);if (flag1 < 0 || flag1>6) { Push(opnd, ch); printf("请输入表达式: "); scanf(" %c", &ch); }else{//比较ch和optr栈顶元素的优先级,返回>,<或者=flag2 = getPriority(GetTop(optr), ch);switch (flag2){case '<'://小于压入optr栈,再读chPush(optr, ch); printf("请输入表达式: ");scanf(" %c", &ch);break;case'>'://大于弹出optr栈顶元素,将opnd元素依次弹出两个求值再压入Pop(optr, theta);//弹出栈顶,用theta接受栈顶元素Pop(opnd, a); Pop(opnd, b);Push(opnd,Operate(b,theta,a));//求值,并压入,这里体现栈的特性先进后出,计算时要注意break;case'='://当等于的时候意味这optr中栈顶左括号和ch(此时为右括号)相遇,此时要将左括号弹出意味着完成括号内的运算Pop(optr, x); printf("请输入表达式: ");scanf(" %c", &ch);break;}}}res = GetTop(opnd) - '0';//循环完成后opnd栈顶即为结果,不过此时是字符型,减去字符0即可printf("结果是%d ", res);DestoryStack(opnd); DestoryStack(optr);
}

测试结果
**在这里插入图片描述**


http://chatgpt.dhexx.cn/article/QSDNGIVu.shtml

相关文章

C语言数据结构篇——栈的顺序存储

作者名&#xff1a;Demo不是emo 主页面链接&#xff1a;主页传送门创作初心&#xff1a;对于计算机的学习者来说&#xff0c;初期的学习无疑是最迷茫和难以坚持的&#xff0c;中后期主要是经验和能力的提高&#xff0c;我也刚接触计算机1年&#xff0c;也在不断的探索&#xf…

C语言数据结构之查找(顺序查找,折半查找)

C语言数据结构之查找&#xff08;顺序查找&#xff0c;折半查找&#xff09; tips&#xff1a;前些天已经学习了树和图的相关知识&#xff0c;今天来总结下两种常用的查找方式&#xff08;顺序查找&#xff0c;折半查找&#xff09;。 为了演示方便&#xff0c;顺序查找和折半…

【C语言数据结构7】--串的实现

串 一、什么是串 串就是我们常说的字符串&#xff0c;它同样是一个线性表。可能有人认为串就是元素为字符的线性表&#xff0c;但这种说法是不准确的。对于普通的线性表&#xff0c;它们关注的往往是单个元素&#xff0c;每个单独的元素都有独立的含义。比如我们用线性表存储…

C语言数据结构——查找(检索)

一、查找的基本概念 查找:查询某个关键字是否在(数据元素集合&#xff09;表中的过程。也称作检索。 查找表: 由同一类型的数据元素&#xff08;或记录&#xff09;构成的集合。 主关键字: 能够惟一区分各个不同数据元素的关键字 次关键字: 通常不能惟一区分各个不同数据元素的…

C语言数据结构——广义表

C语言数据结构中&#xff0c;广义表和数组一样&#xff0c;也是线性表的一种推广&#xff01; 广义表的定义&#xff1a; 广义表 LS 为n&#xff08;n≥0&#xff09;个元素的有穷序列&#xff0c;记作&#xff1a; LS &#xff08;d1, d2, … dn&#xff09; 其中&#xff1…

C语言数据结构——图

一、图的基本概念 图是由顶点集合及顶点间的关系集合组成的一种数据结构。vertex, edge 图G的定义是&#xff1a; G &#xff08;V&#xff0c;E&#xff09; 其中&#xff0c; V {x|x∈某个数据元素集合} E { (x&#xff0c;y)|x&#xff0c;y∈V} &#xff08;无向图&#…

数据结构(c语言版本)

1.基本概念 1.1数据 对客观事物的符号表示&#xff0c;在计算机与科学中是指所有能输入到计算机并被计算机程序处理的符号的总称。 1.2数据元素 是数据的基本单位&#xff0c;在计算机程序中作为一个整体进行考虑和处理 1.3数据对象 是相同性质数据元素的集合&#xff0c…

c语言数据结构

目录 一、数据结构构造概述 1.1、什么是数据结构 1.2、数据的逻辑结构的4种分类 二、线性表 2.1、线性表概述 2.2、顺序表 2.3、链表 2.3.1、链表节点的创建 2.3.2、链表结点遍历 2.3.3、链表结点删除 2.3.4、链表的插入 ​ 三、栈和队列 3.1、栈概述 3.2、栈…

C语言数据结构知识点小结(全)

Catologue C语言数据结构一、基本概念和术语二、时间、空间复杂度&#xff08;1&#xff09;时间复杂度&#xff08;2&#xff09;空间复杂度 三、类C语言有关操作补充1&#xff1a;数组定义补充2&#xff1a;动态内存分配补充3&#xff1a;C中的参数传递 四、线性表&#xff0…

七丶青龙nvjdc部署教程+短信验证登录对接傻妞

青龙nvjdc部署教程短信验证登录对接傻妞Nolanjdc 没有服务器的先自行购买&#xff0c;这里推荐腾讯云2H4G8M首年70–点击购买 青龙面板安装教程 傻妞机器人安装教程 XDD安装教程 QQ交流&#xff1a;1014549449 --------------点击跳转 注丶只能对接一个&#xff0c;要么对接…

手机短信验证

在项目中经常会用到手机短信验证注册&#xff0c;登录等功能&#xff0c;所以我想写一篇文章来给大家提供一个参考。 阿里大于-个人感觉比较好用的短信验证平台&#xff0c;下面是接入阿里大于sdk的步骤。 阿里大于官网&#xff1a;直通车, 进入官网需要注册&#xff0c;注册…

014_关于session实现短信验证登录的前端启动

014_关于session实现短信验证登录的前端启动 1、进入到nginx相对应的文件夹&#xff0c;shfit右键&#xff0c;进入PowerShell并且执行nginx 2、启动我们的nginx,嘿嘿&#xff0c;可以访问我们的前端网页啦&#xff01;&#xff01;&#xff01;它就是模仿我们的大众点评来着…

基于Redis的短信验证登录

基于Redis的短信验证登录 1、用户调用发送短信验证码接口2、用户调用登录/注册接口3、用户调用校验接口4、SpringMvc拦截器注册5、token刷新拦截器6、登录拦截器 1、用户调用发送短信验证码接口 用户调用sendCode()接口&#xff0c;把phone传到后端&#xff0c;后端对phone进行…

使用聚合数据短信API测试(短信验证登录)

搞一手聚合数据短信API测试&#xff08;之前用阿里云的搞过&#xff0c;今天我们用聚合&#xff09; 注册聚合账号&#xff01;聚合官网链接登陆后进入短信服务API&#xff08;免费提供十次&#xff09; 添加自定义模板&#xff08;审核速度看脸&#xff09; 审核成功后得…

android studio 实现短信验证 登录

登录 http://www.mob.com/ 注册 创建项目 加入依赖 贴代码 classpath “com.mob.sdk:MobSDK:2018.0319.1724” apply plugin: ‘com.mob.sdk’ // 在MobSDK的扩展中注册SMSSDK的相关信息 这里使用自己的 appKey appSecret MobSDK {appKey “2e2974aec0” appSecret “1d35b87…

Java简单实现短信验证登录(Session、Redis)

前端设计 <div class"login-form"><div style"display: flex; justify-content: space-between"><el-input style"width: 60%" placeholder"请输入手机号" v-model"form.phone" ></el-input><e…

Vue与Node.js实现手机短信验证登录

手机短信使用的第三方平台是联容云&#xff0c;注册就送8块钱体验费&#xff0c;足够自己用用了&#xff0c;注册完自己建一个应用就能拿到需要使用的配置了&#xff0c;如图 注册完之后1就可以使用了。 Node.js后端使用了Express框架 "js-base64": "^3.7.2&qu…

【青龙面板+诺兰2.0 网页短信验证登录+bot查询】

看这个之前&#xff0c;如果是没搭建过的先看下面这篇哈&#xff0c;如果是跟着下面的搭建完了&#xff0c;出现了机器人5次获取验证码失败&#xff0c;让你用Cookie方式登录的情况&#xff0c;看这篇哈。 前提&#xff1a;自己有服务器&#xff01;这里用的Centos7.6做演示&am…

Springboot实现短信登录验证

Springboot学习笔记——Java实现短信登录验证功能--Servlet/SSM/SpringBoot都可以用 小白记录一下短信验证登入的实现&#xff0c;方便以后可以拿来直接用。 发短信平台&#xff1a;互亿无线 官网地址 登入注册啥的就不说了&#xff0c;新人注册会送十条短信验证&#xff0c;想…

java WEB调用秒嘀科技短信验证接口(实现短信验证登录)

java WEB调用秒嘀科技短信验证接口&#xff08;实现短信验证登录&#xff09; 前言注册秒嘀云账号登录秒嘀云官网 代码 前言 短信验证登咱就不多说了&#xff0c;为什么推荐用秒嘀的呢&#xff0c;应为他会送你10元钱&#xff0c;对于新手来说10元钱&#xff0c;足够你玩了。但…