最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

C++表達(dá)式求值詳解

 更新時(shí)間:2021年10月09日 10:10:26   作者:Computer-hacker  
下面小編就為大家?guī)?lái)一篇淺談C++ 語(yǔ)言中的表達(dá)式求值。小編覺(jué)得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧

一.細(xì)節(jié)處理:

1.注意負(fù)數(shù) 因此要進(jìn)行字符串預(yù)處理

string format(string str) 
{
	int len = str.length();
	for (int i = 0; i < len; i++)
	{
		if (str[i] == '-')
		{
			if (i == 0) { str.insert(0, 1, '0'); }//處理-3*2+1情況
			else if (str[i - 1]=='(') { str.insert(i, 1, '0'); }//處理(-3*4+1)情況
		}
	}
	return str;
}

2.考慮除數(shù)為0

                    case '/':
					if (0 != y) { res = x / y; }
					else { cout << "非法表達(dá)式"; return -1; }
					break;

3.原字符串再加上一個(gè)定界符 '#'

str=str+'#'

4.優(yōu)先級(jí):

1."("未入棧前為3 入棧后為0 2.”)"和"#"為0 3.”+" "-"為1 4.”*"和"/"為2

二.知識(shí)要點(diǎn):

中綴表達(dá)式轉(zhuǎn)為后綴表達(dá)式

1. 首先設(shè)置存儲(chǔ)運(yùn)算符和存儲(chǔ)操作數(shù)兩個(gè)棧 即Symbol[N]和Num[N]且分別對(duì)應(yīng)top2,top1

top1=-1 Symbol[0]='#' //運(yùn)算符棧設(shè)置定界符 top2=0

2.入棧和出棧的規(guī)則 字符串為str

一.若str[i]>='0&&str[i]<='9',則入操作數(shù)棧并繼續(xù)掃描以一個(gè)字符 即Num[++top1]=str[i++]-'0';

二.否則 將當(dāng)前字符str1與運(yùn)算符棧的棧頂元素str2進(jìn)行優(yōu)先級(jí)比較 ,自寫(xiě)比較函數(shù)

例如: str1==‘+' 則若str2==# ,(,) 則返回1 說(shuō)明str1比str2優(yōu)先級(jí)高

1. 此時(shí)若str1優(yōu)先級(jí)大于str2 則將str1入運(yùn)算符棧并繼續(xù)掃描 即 Symbol[++top2]=str[i++]

2.優(yōu)先級(jí)相等則返回0 此時(shí)將運(yùn)算符棧頂元素彈出,并繼續(xù)掃描下一個(gè)字符即 top2-- i++

3.若str1優(yōu)先級(jí)小于str2返回-1,此時(shí)將運(yùn)算符棧頂元素彈出 即op=Symbol[top2--]

并彈出操作數(shù)棧的兩個(gè)元素 即y=Num[top1--],x=Num[top1--] 之后進(jìn)行計(jì)算操作

三.最后 return Num[top1]

三.完整源碼:

#define _CRT_SECURE_NO_WARNINGS
#include<bits/stdc++.h>
using namespace std;
class Expression
{
public:
	Expression(string str);
	~Expression();
	int Compute();
private:
	int Comp(char str1, char str2);
	string str1;
};
Expression::Expression(string str)
{
	this->str1 = str + '#';//以定界符開(kāi)頭
}
Expression :: ~Expression() {}
//將中綴表達(dá)轉(zhuǎn)為后綴表達(dá)
int Expression::Compute()
{
	int Num[100], Symbol[100];//定義存操作數(shù)和運(yùn)算符的兩個(gè)棧
	int i, k, x, y, res;
	char op;
	Symbol[0] = '#';
	int top1 = -1, top2 = 0;
	for (i = 0; str1[i] != '\0';)
	{
		if (str1[i] >= '0' && str1[i] <= '9') { Num[++top1] = str1[i++] - '0'; }
		else {//非操作數(shù)就比較運(yùn)算符優(yōu)先級(jí)
			int cmp = Comp(str1[i], Symbol[top2]);
			if (cmp == 1) { Symbol[++top2] = str1[i++]; }//將運(yùn)算符入棧 并接著掃描下一個(gè)字符
			else if (cmp == 0) { --top2; i++; }//優(yōu)先級(jí)相等 彈棧 并接著掃描下一個(gè)字符
			else {//優(yōu)先級(jí)低 繼續(xù)處理當(dāng)前運(yùn)算符
				y = Num[top1--];//后面的數(shù)要先彈出來(lái) 才不會(huì)算反
				x= Num[top1--];
				op = Symbol[top2--];
				switch (op)
				{
				case '+':
					res = x + y;//將運(yùn)算結(jié)果入棧
					break;
				case '-':
					res = x - y;
					break;
				case '*':
					res = x * y;
					break;
				case '/':
					if (0 != y) { res = x / y; }
					else { cout << "非法表達(dá)式"; return -1; }
					break;
				default:break;
				}
				Num[++top1] = res;
			}
		}
	}
	return Num[top1]; 
}
string format(string str) 
{
	int len = str.length();
	for (int i = 0; i < len; i++)
	{
		if (str[i] == '-')
		{
			if (i == 0) { str.insert(0, 1, '0'); }//處理-3*2+1情況
			else if (str[i - 1]=='(') { str.insert(i, 1, '0'); }//處理(-3*4+1)情況
		}
	}
	return str;
}
int main()
{
	string str;
	int n = 3;
	while (n--)
	{
		cout << "請(qǐng)輸入一個(gè)表達(dá)式: " << endl;
		cin >> str;
		str = format(str);
		Expression E(str);
		int result = E.Compute();
		cout << "表達(dá)式的值的是: " << result << endl;
	}
	return 0;
}
int Expression::Comp(char str1, char str2)//當(dāng)前字符元素和棧頂運(yùn)算符優(yōu)先級(jí)比較
{
	//1代表 str1優(yōu)先級(jí)大于str2 0 代表相等 -1代表小于
	switch (str1)
	{
	case'+':case'-': 
		if (str2 == '#'||str2==')'||str2=='(') { return 1; }//左括號(hào)入隊(duì)列后優(yōu)先級(jí)變?yōu)?
		else { return -1; }
		break;
	case'*':case'/':
		if (str2 == '*' || str2 == '/') { return -1; }
		else  { return 1; }
		break;
	case'(':
		return 1;
		break;
	case')':
		if (str2 == '(') { return 0; }
		else if(str2 == '#') { return 1; }
		else { return -1; }
		break;
	case'#':
		if (str2 == '#') { return 0; }
		else { return -1; }
		break;
	default: break;
	}
}

四.測(cè)試結(jié)果:

總結(jié)

本篇文章就到這里了,希望能夠給你帶來(lái)幫助,也希望您能夠多多關(guān)注腳本之家的更多內(nèi)容!

相關(guān)文章

  • 詳解C++-(=)賦值操作符、智能指針編寫(xiě)

    詳解C++-(=)賦值操作符、智能指針編寫(xiě)

    C++的智能指針是克服C++大坑的非常有用的的手段,之所以說(shuō)它智能,是因?yàn)樗鼮槌绦騿T克服了重要的編程問(wèn)題——懸掛指針,下面通過(guò)本文給大家分享C++-(=)賦值操作符、智能指針編寫(xiě),感興趣的朋友一起看看吧
    2018-03-03
  • QSS樣式表實(shí)現(xiàn)界面換膚功能

    QSS樣式表實(shí)現(xiàn)界面換膚功能

    這篇文章主要介紹了QSS樣式表實(shí)現(xiàn)界面換膚功能,對(duì)QSS樣式表進(jìn)行簡(jiǎn)單介紹,本文通過(guò)實(shí)例代碼給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2022-10-10
  • C語(yǔ)言與Lua之間的相互調(diào)用詳解

    C語(yǔ)言與Lua之間的相互調(diào)用詳解

    這篇文章主要給大家介紹了關(guān)于C語(yǔ)言與Lua之間的相互調(diào)用的相關(guān)資料,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧。
    2018-01-01
  • OpenCV圖像分割中的分水嶺算法原理與應(yīng)用詳解

    OpenCV圖像分割中的分水嶺算法原理與應(yīng)用詳解

    這篇文章主要為大家詳細(xì)介紹了OpenCV圖像分割中的分水嶺算法原理與應(yīng)用,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2018-01-01
  • 基于C++實(shí)現(xiàn)柏林噪聲算法(Perlin?Noise)

    基于C++實(shí)現(xiàn)柏林噪聲算法(Perlin?Noise)

    Perlin噪聲(Perlin?noise,又稱為柏林噪聲)指由Ken?Perlin發(fā)明的自然噪聲生成算法,具有在函數(shù)上的連續(xù)性,并可在多次調(diào)用時(shí)給出一致的數(shù)值。本文將用C++實(shí)現(xiàn)柏林噪聲算法,感興趣的可以了解一下
    2023-03-03
  • C++簡(jiǎn)單又輕松的講解類和對(duì)象中友元函數(shù)

    C++簡(jiǎn)單又輕松的講解類和對(duì)象中友元函數(shù)

    采用類的機(jī)制后實(shí)現(xiàn)了數(shù)據(jù)的隱藏與封裝,類的數(shù)據(jù)成員一般定義為私有成員,成員函數(shù)一般定義為公有的,依此提供類與外界間的通信接口。但是,有時(shí)需要定義一些函數(shù),這些函數(shù)不是類的一部分,但又需要頻繁地訪問(wèn)類的數(shù)據(jù)成員,這時(shí)可以將這些函數(shù)定義為該類的友元函數(shù)
    2022-06-06
  • 利用Qt實(shí)現(xiàn)網(wǎng)絡(luò)數(shù)據(jù)報(bào)文大小端數(shù)據(jù)的收發(fā)

    利用Qt實(shí)現(xiàn)網(wǎng)絡(luò)數(shù)據(jù)報(bào)文大小端數(shù)據(jù)的收發(fā)

    大小端(Endianness)是計(jì)算機(jī)體系結(jié)構(gòu)的一個(gè)術(shù)語(yǔ),它描述了多字節(jié)數(shù)據(jù)在內(nèi)存中的存儲(chǔ)順序,下面我們來(lái)看看如何利用Qt實(shí)現(xiàn)網(wǎng)絡(luò)數(shù)據(jù)報(bào)文大小端數(shù)據(jù)的收發(fā)吧
    2024-11-11
  • C語(yǔ)言中strcmp的實(shí)現(xiàn)原型

    C語(yǔ)言中strcmp的實(shí)現(xiàn)原型

    這篇文章主要介紹了C語(yǔ)言中strcmp的實(shí)現(xiàn)原型的相關(guān)資料,這里提供實(shí)例幫助大家理解這部分內(nèi)容,希望能幫助到大家,需要的朋友可以參考下
    2017-08-08
  • C語(yǔ)言實(shí)現(xiàn)strlen的三種方法小結(jié)

    C語(yǔ)言實(shí)現(xiàn)strlen的三種方法小結(jié)

    本文主要介紹了C語(yǔ)言實(shí)現(xiàn)strlen的三種方法小結(jié),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2023-06-06
  • C語(yǔ)言數(shù)據(jù)結(jié)構(gòu)之 折半查找實(shí)例詳解

    C語(yǔ)言數(shù)據(jù)結(jié)構(gòu)之 折半查找實(shí)例詳解

    這篇文章主要介紹了C語(yǔ)言數(shù)據(jù)結(jié)構(gòu)之 折半查找實(shí)例詳解的相關(guān)資料,需要的朋友可以參考下
    2017-06-06

最新評(píng)論

静安区| 成都市| 永兴县| 柳州市| 紫金县| 垦利县| 抚远县| 达州市| 巴彦淖尔市| 泽普县| 柞水县| 太湖县| 康乐县| 平塘县| 长海县| 枞阳县| 黄梅县| 和硕县| 通江县| 巴彦县| 卢氏县| 芒康县| 莱芜市| 景宁| 竹北市| 红原县| 宜宾市| 道真| 庆云县| 利津县| 茌平县| 蓬莱市| 潍坊市| 闸北区| 运城市| 兴城市| 蓝山县| 遂昌县| 定襄县| 西宁市| 大埔县|