日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

java加减乘除运算顺序_java 实现加减乘除混合运算

發布時間:2023/12/2 编程问答 27 豆豆
生活随笔 收集整理的這篇文章主要介紹了 java加减乘除运算顺序_java 实现加减乘除混合运算 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

初衷:解決小學一年級到四年級 基本加減乘除混合運算

基本思路:

表達式:100+3+2-200+(10000/5+(100/2))

此類表達式我們稱之為中綴表達式(運算符在數字的中間),如果我們稍加轉換,轉化為

100, 3, +, 2, +, 200, -, 10000, 5, /, 100, 2, /, +, +? 轉化后的表達式我們稱之為后綴表達式(運算符在數字的后面),先不考慮該表達式是怎么來的,后面我們將詳細介紹由中綴表達式轉化為后綴表達式的實現過程;我們借助棧的數據結構(后進先出)來輔助我們解決這個問題,拿到轉化后的結果 我們先創建一個空棧,從左往右開始運算,具體的運算邏輯為:

1.遇到數字則入棧

2.遇到運算符號 則將棧頂兩元素出棧

3.根據運算符號進行運算并將運算結果入棧

4.表達式結束 則將棧頂元素 取出

我們先靠手來計算一下結果為1955;現在我們用這個規律來進行分析,

第一步:數字100先入棧;

第二步:數字3入棧;

第三步: + 則將棧頂的數字3取出,此時棧頂為100 再將數字100取出,將相加后的結果103入棧;

第四步:數字2入棧;

第五步:+ 將棧頂數字2取出,繼續取出棧頂數字103,將相加后的結果105入棧;

第六步:200入棧;

第七步:- 將棧頂數字200 取出,繼續取出棧頂數字105 將相減后結果 -95 入棧;

第八步:數字10000入棧;

第九步:數字5入棧;

第十步:/ 將棧頂數字5 取出 繼續取出棧頂數字10000,計算結果為2000,將2000入棧;

第十一步:數字100入棧;

第十二步:數字2入棧;

第十三步:/ 棧頂數字 2 和棧頂數字100 結果為50 入棧;

第十四步:+ 棧頂數字50 和棧頂數字?2000?計算結果為2050 入棧;

第十五步:+ 棧頂數字2050 和棧頂數字-95 計算結果為 1955 入棧;

第十六步:遍歷結束,取出棧頂數字 1955

至此結果已經出來了,最終的計算結果為1955

現在來解釋剛剛的疑問,后綴表達式該怎么來生成呢??

好了現在我們來一點一點解開未解之謎

1.中綴表達式從左往右遍歷,遇到數字則輸出

2. 遇到左括號,入棧;遇到右括號 則從棧頂取 一直到取到左括號為止;遇到運算符,優先級不低于當前符號出棧并輸出,直到取到比當前優先級低為止(+,-優先級相等,* / 優先級相等,+- 優先級低于 * /)

3.表達式遍歷結束 棧內符號依次出棧

還是剛剛的表達式:100+3+2-200+(10000/5+(100/2))

我們來按照這個步驟來分析一下

先創建一個空棧

第一步:數字100輸出;

第二步:+ 入棧;

第三步:數字3 輸出;

第四步:+ 棧中沒有優先級比+低 故棧中+出棧輸出,此處+入棧;

第五步:數字2輸出;

第六步:-?棧中沒有優先級比-低 故棧中+出棧輸出,此處-入棧;

第七步:數字200 輸出;

第八步:+?棧中沒有優先級比+低 故棧中-出棧輸出,此處+ 入棧;

第九步:符號(入棧;

第十步:數字10000輸出;

第十一步:/ 棧中+ (優先級都沒有/ 高 故/入棧;

第十二步:數字5 輸出;

第十三步:+ 棧頂為/ 優先級高于+ 故+ 入棧/出棧輸出;

第十四步:(入棧;

第十五步:數字 100 輸出;

第十六步:/ 棧頂為( 此處/入棧;

第十七步:數字2 輸出;

第十八步:),找到棧頂最近的(之間的符號/出棧輸出,(出棧;

第十九步:),到最近的(之間的符號+出棧輸出,(出棧;

第二十步:遍歷結束,棧中依次出棧+;

從上往下 背景標紅部分為后綴表達式的輸出順序

下面為java代碼實現 僅供參考

package com.fx.hfirst.strategy;

import java.util.ArrayList;

import java.util.HashMap;

import java.util.List;

import java.util.Map;

import java.util.Stack;

import java.util.regex.Pattern;

public class Compute {

/**

* @param args

*/

public static void main(String[] args) {

String data = "100+3+2-200+(10000/5+(100/2))";

String[] dataArray = getDataArray(data);

String[] postfixArray = getPostFix(dataArray);

computeWithPostFix(postfixArray);

}

private static String[] getDataArray(String data) {

if (data == null || "".equals(data.trim()) || data.trim().length() < 1) {

return null;

}

int dataLength = data.length();

String[] dataArray = new String[dataLength];// 根據字符串的長度創建數組

int top = 0;

String numStr = "";

for (int i = 0; i < dataLength; i++) {

char datai = data.charAt(i);

String num = String.valueOf(datai);

if (isNum(num)) {// 數字

numStr += num;

if (i + 1 == dataLength) {

dataArray[top] = numStr;

top++;

}

} else {

if (!"".equals(numStr)) {// numStr 存在

dataArray[top] = numStr;// 數字存放到結果數組中

numStr = "";// 還原

top++;// 指針下移

}

// 符號

dataArray[top] = num;

top++;// 指針下移

}

}

return removeNull(dataArray, top);

}

/**

* 獲取后綴表達式

*

* @param data

* @return

*/

private static String[] getPostFix(String[] dataArray) {

if (dataArray == null || dataArray.length < 1) {

return null;

}

// 1.遍歷數組 數字輸出

// 2.若是符號 則判斷和棧頂符號的優先級 是右括號 或者優先級低于棧頂符號(乘除高于加減)則棧頂元素依次出棧 輸出 并將當前符號入棧

// 3.數組結束 棧內符號依次出棧

int dataLength = dataArray.length;

Stack dataStack = new Stack();

String[] dataBuffer = new String[dataLength];

int top = 0;

for (int i = 0; i < dataLength; i++) {

String datai = dataArray[i];

if (isNum(datai)) {// 數字

dataBuffer[top] = datai;

top++;// 指針下移

} else if (isLeftBracket(datai)) {// 左括號

dataStack.push(datai);// 壓棧

} else if (ComputeEnum.isCompute(datai)) {// 運算符

List lessThenMeList = getNotLessThenMeta(dataStack,

datai);

if (lessThenMeList != null && !lessThenMeList.isEmpty()) {

for (String lessThen : lessThenMeList) {// 小于當前運算符的符號輸出

dataBuffer[top] = lessThen;

top++;// 指針下移

}

}

dataStack.push(datai);// 當前元素入棧

} else if (isRightBracket(datai)) {// 右括號 查找到最近左括號之間的所有符號 出棧

List betweenLeftBracketList = getBetweenLeftBracketMeta(dataStack);

if (betweenLeftBracketList != null

&& !betweenLeftBracketList.isEmpty()) {

for (String between : betweenLeftBracketList) {// 小于當前運算符的符號輸出

dataBuffer[top] = between;

top++;// 指針下移

}

}

} else {

System.err.println("請注意中英文符號,檢查出包含不支持的運算符!");

return null;

}

}

while (!dataStack.isEmpty()) {

dataBuffer[top] = dataStack.pop();

top++;// 指針下移

}

return removeNull(dataBuffer, top);

}

// 根據后綴表達式計算出結果 并打印

private static void computeWithPostFix(String[] postfixArray) {

if (postfixArray == null || postfixArray.length < 1) {

System.err.println("postfixArray is null !");

return;

}

// 1.遇到數字則入棧

// 2.遇到運算符號 則將棧頂兩元素出棧

// 3.將運算結果入棧

// 4.數組遍歷結束 將棧頂元素 取出

Stack stack = new Stack();

for (String meta : postfixArray) {

if (isNum(meta)) {// 數字

stack.push(meta);

} else if (ComputeEnum.isCompute(meta)) {// 運算符號

double pop = Double.parseDouble(stack.pop());

double popNext = Double.parseDouble(stack.pop());

double result = compute(pop, popNext, meta);

stack.push(String.valueOf(result));

}

}

System.out.println("運算結果為:" + stack.pop());

}

private static double compute(double pop, double popNext, String meta) {

double result = 0;

ComputeEnum compute = ComputeEnum.get(meta);

switch (compute) {

case plus:// 加

result = popNext + pop;

break;

case minus:// 減

result = popNext - pop;

break;

case multiply:// 乘

result = popNext * pop;

break;

case divide:// 除

if ((pop < 0.000000001) && (pop > -0.000000001)) {

System.err.println("被除數不能為0!");

break;

}

result = popNext / pop;

break;

}

return result;

}

private static List getBetweenLeftBracketMeta(

Stack dataStack) {

if (dataStack == null || dataStack.size() < 1) {

return null;

}

List list = new ArrayList(dataStack.size());

while (!dataStack.isEmpty()) {

String pop = dataStack.pop();// 棧頂元素出棧

if (isLeftBracket(pop)) {

break;

}

list.add(pop);

}

return list;

}

/**

* 取出所有不比自己優先級低的元素

*

* @param dataStack

* @param datai

* @return

*/

private static List getNotLessThenMeta(Stack dataStack,

String datai) {

if (dataStack == null || dataStack.size() < 1) {

return null;

}

ComputeEnum computei = ComputeEnum.get(datai);

List list = new ArrayList(dataStack.size());

while (!dataStack.isEmpty()) {

String pop = dataStack.peek();// 棧頂元素

ComputeEnum compute = ComputeEnum.get(pop);

if (compute == null) {

break;

}

if (compute.level < computei.level) {

break;

} else {// 優先級高于當前符號 出棧

dataStack.pop();

list.add(pop);

}

}

return list;

}

private static String[] removeNull(String[] dataArray, int size) {

String[] dataResult = new String[size];

System.arraycopy(dataArray, 0, dataResult, 0, dataResult.length);

return dataResult;

}

private static boolean isNum(String num) {

String reg = "^\\d+$";

return Pattern.compile(reg).matcher(num).find();

}

/**

* 左括號

*

* @param num

* @return

*/

private static boolean isLeftBracket(String num) {

return "(".equals(num);

}

/**

* 右括號

*

* @param num

* @return

*/

private static boolean isRightBracket(String num) {

return ")".equals(num);

}

}

enum ComputeEnum {

plus("+", 0), // 加法

minus("-", 0), // 減法

multiply("*", 1), // 乘法

divide("/", 1), // 除法

;

private static Map dataMap = new HashMap();

static {

dataMap.put(plus.code, plus);

dataMap.put(minus.code, minus);

dataMap.put(multiply.code, multiply);

dataMap.put(divide.code, divide);

}

public String code;

public int level;

private ComputeEnum(String code, int level) {

this.code = code;

this.level = level;

}

public static ComputeEnum get(String code) {

return dataMap.get(code);

}

public static boolean isCompute(String code) {

return dataMap.containsKey(code);

}

}

博客中若有錯誤,歡迎指正,我們一起來共同完善!

總結

以上是生活随笔為你收集整理的java加减乘除运算顺序_java 实现加减乘除混合运算的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。