逆波兰(非与或)表达式原理及C++代码实现
p.p1 { margin: 0; font: 11px Menlo; color: rgba(209, 47, 27, 1); background-color: rgba(255, 255, 255, 1) }
运算符表达式:(a||b)||(c)&&d
分析语法
1 String16 analyzeData(const uint16_t* str, int &i)
2 {
3 int temp = i++;
4 while(!((str[i] == C16('&') && str[i+1] == C16('&'))
5 || (str[i] == C16('|') && str[i+1] == C16('|'))
6 || (str[i] == C16('!') && str[i+1] == C16('!'))
7 || str[i] == C16('(') || str[i] == C16(')') || str[i] == C16('\0'))) {
8 i++;
9 }
10 return dice::String16(str+temp,i-temp);
11 }
12
13 bool isCalChar(const uint16_t key,const uint16_t nextKey)
14 {
15 if((key == C16('&') && nextKey == C16('&'))
16 || (key == C16('|') && nextKey == C16('|'))
17 || (key == C16('!') && nextKey == C16('!'))
18 || key == C16('(') || key == C16(')')) {
19 return true;
20 }
21 return false;
22 }
23
24 vector<CustomMap> analyzeData(const uint16_t* keyword) {
25 int i = 0;
26 String16 data;
27 /* 存放运算符表达式的栈 */
28 sgi::stack<uint16_t> operChar;
29 /* 存放后缀表达式 */
30 vector<CustomMap> customDataList;
31 /* 判断输入的中缀表达式是否合法 */
32 {
33 /* 将中缀表达式转换为后缀表达式 */
34 for(i = 0; keyword[i] != '\0'; i++) {
35 /* 如果该字符为数字,解析该数字,并压入栈 */
36 if(isCalChar(keyword[i],keyword[i+1]) != true) {
37 data = analyzeData(keyword,i);
38 dice::CustomMap customMap;
39 customMap.customName = data;
40 customMap.operatorType = OperatorTypeNone;
41 customMap.customCode = 0l;
42 customDataList.push_back(customMap);
43 i--;
44 }
45 else if(keyword[i] == C16('(')) {
46 operChar.push(keyword[i]);
47 }
48 else if(keyword[i] == C16(')')) {
49 uint16_t operTemp[2] = {0};
50
51 operTemp[0] = operChar.top();
52
53 while(operTemp[0] != C16('(')) {
54 String16 strtemp(operTemp);
55 dice::CustomMap customMap;
56 customMap.customName = operTemp;//运算符
57 switch (operTemp[0]) {
58 case C16('!'):
59 customMap.operatorType = OperatorTypeDifference;
60 break;
61 case C16('&'):
62 customMap.operatorType = OperatorTypeIntersect;
63 break;
64 case C16('|'):
65 customMap.operatorType = OperatorTypeUnite;
66 break;
67 default:
68 break;
69 }
70 customMap.customCode = 0l;
71 customDataList.push_back(customMap);
72 operChar.pop();
73 operTemp[0] = operChar.top();
74 }
75 operChar.pop();
76 }
77 else if((keyword[i] == C16('&') &&keyword[i+1] == C16('&'))
78 || (keyword[i] == C16('|')&&keyword[i+1] == C16('|'))
79 || (keyword[i] == C16('!') && keyword[i+1] == C16('!'))
80 ) {
81 uint16_t operTemp[2] = {0};
82 /* 全部出栈,但是碰到 '('就要停止出栈 */
83 while(operChar.size() != 0) {
84 operTemp[0] = operChar.top();
85 if(operTemp[0] == C16('(')) {
86 break;
87 }
88 operChar.pop();
89 dice::CustomMap customMap;
90 customMap.customName = operTemp;//运算符
91 switch (operTemp[0]) {
92 case C16('!'):
93 customMap.operatorType = OperatorTypeDifference;
94 break;
95 case C16('&'):
96 customMap.operatorType = OperatorTypeIntersect;
97 break;
98 case C16('|'):
99 customMap.operatorType = OperatorTypeUnite;
100 break;
101 default:
102 break;
103 }
104 customMap.customCode = 0l;
105 customDataList.push_back(customMap);
106 }
107 /*将当前的表达式符号入栈*/
108 operChar.push(keyword[i]);
109 i++;
110 }
111 }
112 /* 存放表达式的栈可能还有数据 */
113 while (!operChar.empty()) {
114 uint16_t operTemp[2] = {0};
115 operTemp[0] = operChar.top();
116 operChar.pop();
117
118 dice::CustomMap customMap;
119 customMap.customName = operTemp;//运算符
120 switch (operTemp[0]) {
121 case C16('!'):
122 customMap.operatorType = OperatorTypeDifference;
123 break;
124 case C16('&'):
125 customMap.operatorType = OperatorTypeIntersect;
126 break;
127 case C16('|'):
128 customMap.operatorType = OperatorTypeUnite;
129 break;
130 default:
131 break;
132 }
133 customMap.customCode = 0l;
134 customDataList.push_back(customMap);
135 }
136 }
137 // 输出表达式代码
138 // vector<CustomMap>::iterator it;
139 //
140 // String16 strTemp;
141 // for(it = customDataList.begin(); it != customDataList.end(); it++) {
142 // dice::CustomMap customMap = (*it);
143 // strTemp = (*it).customName;
144 // printf("operatorType = %d\n",customMap.operatorType);
145 // api_print(strTemp.c_str());
146 // }
147 return customDataList;
148 }
解析处理数据
1 void getCustomIndexData(SearchDataAccessorIndex* indexDataAccessor, int32_t cityId, const vector<CustomMap>& cutomMapList, sgi::vector<int32_t>& poiIdxArray, int32_t& poiIdxCount) {
2
3 int32_t* loadIndexArray = NULL;
4 int32_t loadIndexCnt = 0u;
5 SearchStatus loadStatus = SearchStatusFailed;
6 SearchStatus returnStatus = SearchStatusFailed;
7 stack<CustomIdxData*> customStakData;
8 CustomIdxData* customIdxData1;
9 CustomIdxData* customIdxData2;
10 assert(indexDataAccessor);
11 vector<CustomMap>::iterator it;
12 CustomMap* cutomMap;
13 do {
14 poiIdxArray.clear();
15 poiIdxCount = 0;
16 returnStatus = SearchStatusSucceed;
17 for(it = cutomMapList.begin(); it != cutomMapList.end(); it++) {
18 cutomMap = it;
19 switch (cutomMap->operatorType) {
20 case OperatorTypeNone:
21 /* 获取单充电桩索引 */
22 loadStatus = indexDataAccessor->getPoiIdxListByCustomCode(cityId, cutomMap->customCode, (const int32_t*&)loadIndexArray, loadIndexCnt);
23 if (loadStatus == SearchStatusSucceed || loadStatus ==SearchStatusNoData) {
24 CustomIdxData* customIdxData = new CustomIdxData();
25 customIdxData->poiIdxArray.resize(loadIndexCnt);
26 customIdxData->poiIdxArray.assign(loadIndexArray, loadIndexArray + loadIndexCnt);
27 customIdxData->poiIdxCount = loadIndexCnt;
28 customStakData.push(customIdxData);
29 } else {
30 returnStatus = SearchStatusFailed;
31 }
32 break;
33 case OperatorTypeIntersect: /* 交集 */
34 customIdxData1 = customStakData.top();
35 customStakData.pop();
36 customIdxData2 = customStakData.top();
37 customStakData.pop();
38 customIdxData1->poiIdxCount = sgi::set_intersection(customIdxData1->poiIdxArray.begin(), customIdxData1->poiIdxArray.begin() + customIdxData1->poiIdxCount,
39 customIdxData2->poiIdxArray.begin(), customIdxData2->poiIdxArray.begin() + customIdxData2->poiIdxCount,
40 customIdxData1->poiIdxArray.begin()) - customIdxData1->poiIdxArray.begin();
41 delete customIdxData2;
42 customStakData.push(customIdxData1);
43 break;
44 case OperatorTypeUnite: /* 并集 */
45 {
46 customIdxData1 = customStakData.top();
47 customStakData.pop();
48 customIdxData2 = customStakData.top();
49 customStakData.pop();
50 CustomIdxData* customUniteIdxData= new CustomIdxData();
51 customUniteIdxData->poiIdxArray.resize(customIdxData1->poiIdxCount + customIdxData2->poiIdxCount);
52 customUniteIdxData->poiIdxCount = sgi::set_union(customIdxData1->poiIdxArray.begin(), customIdxData1->poiIdxArray.begin() + customIdxData1->poiIdxCount,
53 customIdxData2->poiIdxArray.begin(), customIdxData2->poiIdxArray.begin() + customIdxData2->poiIdxCount,
54 customUniteIdxData->poiIdxArray.begin()) - customUniteIdxData->poiIdxArray.begin();
55 delete customIdxData1;
56 delete customIdxData2;
57 customStakData.push(customUniteIdxData);
58 }
59 break;
60 case OperatorTypeDifference: /* 差集 */
61 customIdxData1 = customStakData.top();
62 customStakData.pop();
63 customIdxData2 = customStakData.top();
64 customStakData.pop();
65 customIdxData1->poiIdxCount = sgi::set_difference(customIdxData1->poiIdxArray.begin(), customIdxData1->poiIdxArray.begin() + customIdxData1->poiIdxCount,
66 customIdxData2->poiIdxArray.begin(), customIdxData2->poiIdxArray.begin() + customIdxData2->poiIdxCount,
67 customIdxData1->poiIdxArray.begin()) - customIdxData1->poiIdxArray.begin();
68 delete customIdxData2;
69 customStakData.push(customIdxData1);
70 break;
71 default:
72 returnStatus = SearchStatusFailed;
73 break;
74 }
75
76 if (returnStatus != SearchStatusSucceed) {
77 break;
78 }
79 }
80 if (returnStatus != SearchStatusSucceed) {
81 break;
82 }
83 customIdxData1 = customStakData.top();
84 customStakData.pop();
85 poiIdxCount = customIdxData1->poiIdxCount;
86 if ( poiIdxCount > 0) {
87 poiIdxArray.swap(customIdxData1->poiIdxArray);
88 }
89 delete customIdxData1;
90 if (poiIdxCount <= 0) {
91 returnStatus = SearchStatusNoData;
92 break;
93 }
94 } while (0);
95
96 return(returnStatus);
97 }
逆波兰(非与或)表达式原理及C++代码实现的更多相关文章
- 逆波兰(加、减、乘、除、括号)表达式原理及C++代码实现
当我们输入一个数学表达式,是中缀表达式,我们首先转换为后缀表达式(逆波兰表达式),然后再进行求值. 代码思路: (1)首先对输入的中缀表达式合法性进行判断,bool isStringLegal(con ...
- c# 逆波兰式实现计算器
语文不好,不太会组织语言,希望不要太在意. 如题,先简要介绍一下什么是逆波兰式 通常我们在写数学公式的时候 就是a+b+c这样,这种表达式称为中缀表达式,逆波兰式又称为后缀表达式,例如a+b 后缀 ...
- [LeetCode]Evaluate Reverse Polish Notation(逆波兰式的计算)
原题链接:http://oj.leetcode.com/problems/evaluate-reverse-polish-notation/ 题目描述: Evaluate the value of a ...
- javascript:逆波兰式表示法计算表达式结果
逆波兰式表示法,是由栈做基础的表达式,举个例子: 5 1 2 + 4 * + 3 - 等价于 5 + ((1 + 2) * 4) - 3 原理:依次将5 1 2 压入栈中, 这时遇到了运算符 + ...
- CH BR4思考熊(恒等有理式-逆波兰表达式求值)
恒等有理式 总时限 10s 内存限制 256MB 出题人 fotile96 提交情况 4/43 描述 给定两个有理式f(X)与g(X),判断他们是否恒等(任意A,如果f(A)与g(A)均有定义,那么f ...
- leetcode算法学习----逆波兰表达式求值(后缀表达式)
下面题目是LeetCode算法:逆波兰表达式求值(java实现) 逆波兰表达式即后缀表达式. 题目: 有效的运算符包括 +, -, *, / .每个运算对象可以是整数,也可以是另一个逆波兰表达式.同 ...
- LeetCode 150:逆波兰表达式求值 Evaluate Reverse Polish Notation
题目: 根据逆波兰表示法,求表达式的值. 有效的运算符包括 +, -, *, / .每个运算对象可以是整数,也可以是另一个逆波兰表达式. Evaluate the value of an arithm ...
- Java 实现《编译原理》中间代码生成 -逆波兰式生成与计算 - 程序解析
Java 实现<编译原理>中间代码生成 -逆波兰式生成与计算 - 程序解析 编译原理学习笔记 (一)逆波兰式是什么? 逆波兰式(Reverse Polish notation,RPN,或逆 ...
- JavaScript实现计算后缀表达式(逆波兰表达式)以及将中缀表达式转为后缀表达式
逆波兰表达式,它的语法规定,表达式必须以逆波兰表达式的方式给出.逆波兰表达式又叫做后缀表达式.这个知识点在数据结构和编译原理这两门课程中都有介绍,下面是一些例子: 正常的表达式 逆波兰表达式 a+b ...
随机推荐
- 生成&添加 SSH公钥
生成&添加 SSH公钥 生成 打开 Terminal(终端) 生成命令 ssh-keygen -t ed25519 -C "your_email@example.com" ...
- 【豆科基因组】普通豆/菜豆/四季豆Common bean (Phaseolus vulgaris L.) 683个自然群体重测序2020NG
目录 一.来源 二.结果 683份材料重测序 地方种landraces和育种品系breeding lines的多样性 表型和基因-环境互作(G by E) 菜豆产量潜力相关的MTAs(显著关联位点) ...
- 【Python小试】计算蛋白序列中指定氨基酸所占的比例
编码 from __future__ import division def get_aa_percentage(protein, aa_list=['A','I','L','M','F','W',' ...
- 你不知道的iostat
1. 作用 iostat是I/O statistics(输入/输出统计)的缩写,iostat工具将对系统的磁盘操作活动进行监视.它的特点是汇报磁盘活动统计情况,同时也会汇报出CPU使用情况 ...
- 变量、内存区域、MDK文件(map、htm)
变量分为:局部变量和全局变量 局部变量:函数体内部定义的变量,作用域为函数内部,static声明(静态局部变量)该变量则函数调用结束后不消失而保留值,分配的存储空间不释放. 全局变量:函数体外部定义的 ...
- accommodate, accompany
accommodate 词源: to make fit, suitable; 近/反义词: adapt, adjust, lodge; disoblige, incommode, misfit Lod ...
- 18. MYSQL 字符编码配置
MYSQL 5.7版本的my.ini 在C盘隐藏文件夹下 C:\ProgramData\MySQL\MySQL Server 5.7 [client] default-character-set=ut ...
- FileReader (三) - 网页拖拽并预显示图片简单实现
以下是一个很贱很简单的一个 在网页上图拽图片并预显示的demo. 我是从https://developer.mozilla.org/en-US/docs/Web/API/FileReader#Stat ...
- git pull、git fetch、git merge、git rebase的区别
一.git pull与git fetch区别 1.两者的区别 两者都是更新远程仓库代码到本地. git fetch相当于是从远程获取最新版本到本地,不会自动merge. 只是将远程仓库最新 ...
- 利用extern共享全局变量
方法: 在xxx.h中利用extern关键字声明全局变量 extern int a; 在xxx.cpp中#include<xxx.h> 再定义 int a; 赋不赋初值无所谓,之后该全局变 ...