android 计算器

来源:互联网 发布:手机怎么查自己淘宝id 编辑:程序博客网 时间:2024/05/19 03:26

1、核心:

(1)计算器的每一次输入要检查合法性

(2)计算的核心是把从文本编辑框获得的内容进行分离,将数字压入数字栈,符号进行优先级判断后压入符号栈,然后依次取出运算得到结果。


(3)计算流程图(由于电脑之前重装了,没有亿图,流程图不多就用写的了)


(4)重要代码

1、这个函数是对输入的运算式进行检查,如果输入的有错误,就进行提示,并且将输入框锁定。

 (代码注释比较多,这里就不多说了)

private void TipChecker(String tipcommand1,String tipcommand2){

    //Tipcode1表示数据类型,Tipcode2表示名词类型解释

    int Tipcode1=0,Tipcode2=0;

    //表示命令类型

    int tiptype1=0,tiptype2=0;

    //括号数

    int bracket=0;

    //+-*/^)根号 不能作为第一位

if(tipcommand1.compareTo("#")==0&&(tipcommand2.compareTo("÷")==0||tipcommand2.compareTo("")==0||tipcommand2.compareTo("+")==0||tipcommand2.compareTo(")")==0||tipcommand2.compareTo("")==0||tipcommand2.compareTo("^")==0)){Tipcode1=-1;}

 //定义存储字符串中最后一位的类型

 elseif(tipcommand1.compareTo("#")!=0){if(tipcommand1.compareTo("(")==0){tiptype1=1;}elseif(tipcommand1.compareTo(")")==0){tiptype1=2;}else if(tipcommand1.compareTo(".")==0){tiptype1=3;}else if("0123456789".indexOf(tipcommand1)!=-1){tiptype1=4;}

     else if("+-×÷".indexOf(tipcommand1)!=-1){tiptype1=5;}else if("^".indexOf(tipcommand1)!=-1){tiptype1=6;}else if("sincostanlnlogn!".indexOf(tipcommand1)!=-1){tiptype1=7;}

     //定义欲输入的按键类型

     if(tipcommand2.compareTo("(")==0){tiptype2=1;}else if(tipcommand2.compareTo(")")==0){tiptype2=2;}else if(tipcommand2.compareTo(".")==0){tiptype2=3;}else if("0123456789".indexOf(tipcommand1)!=-1){tiptype2=4;}

     else if("+-×÷".indexOf(tipcommand2)!=-1){tiptype2=5;}else if("^".indexOf(tipcommand2)!=-1){tiptype2=6;}else if("sincostanlnlogn!".indexOf(tipcommand2)!=-1){tiptype2=7;}

     switch(tiptype1){

     case 1://左括号后面直接接右括号,“+*/(符号不算),或者“根号^

     if(tiptype2==2||(tiptype2==5&&tipcommand2.compareTo("-")!=0)||tiptype2==6) Tipcode1=1; break;

     case 2://右括号后面接左括号、数字、“+-*/sin^...

     if(tiptype2==1||tiptype2==3||tiptype2==4||tiptype2==7) Tipcode1=2; break;

     case 3://"."后面接左括号或者sincon...

     if(tiptype2==1||tiptype2==7) Tipcode1=3;

     //连续输入两个“.

     if(tiptype2==3) Tipcode1=8; break;

     case 4://数字后面直接接左括号或者“sincon...

     if(tiptype2==1||tiptype2==7) Tipcode1=4;break;

     case 5://+-×÷后面直接接右括号,+-×÷根号^

     if(tiptype2==2||tiptype2==5||tiptype2==6) Tipcode1=5;break;

     case 6://根号^后面直接接右括号,+-×÷根号^以及“sincos...

     if(tiptype2==2||tiptype2==5||tiptype2==6||tiptype2==7) Tipcode1=6;break;

     case 7://sincos...后面直接接右括号“+-*/根号^”以及sincos

     if(tiptype2==2||tiptype2==5||tiptype2==6||tiptype2==7) Tipcode1=7;break;

     }

     }//(tipcommand1.compareTo("#")!=0)

         //检测小数点的重复性,Tipcondel=0,表明满足前面的规则

         if(Tipcode1==0 &&tipcommand2.compareTo(".")==0){

         int tip_point=0;

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

         if(Tipcommand[i].compareTo(".")==0)

         tip_point++;

             //若出现以下几个运算符之一,小数点计数清零

             if(Tipcommand[i].compareTo("sin")==0||Tipcommand[i].compareTo("cos")==0||Tipcommand[i].compareTo("tan")==0||

             Tipcommand[i].compareTo("log")==0||Tipcommand[i].compareTo("ln")==0||Tipcommand[i].compareTo("n!")==0

             ||Tipcommand[i].compareTo("")==0||Tipcommand[i].compareTo("^")==0||Tipcommand[i].compareTo("+")==0

             ||Tipcommand[i].compareTo("-")==0||Tipcommand[i].compareTo("×")==0||Tipcommand[i].compareTo("÷")==0

             ||Tipcommand[i].compareTo("(")==0||Tipcommand[i].compareTo(")")==0){tip_point=0;}

         }

         tip_point++;

         //若小数点计数大于1,表明小数点重复了

         if(tip_point>1){Tipcode1 = 8;}

         }//if(Tipcode1==0 &&tipcommand2.compareTo(".")==0){}

         //检测右括号是否匹配

         if(Tipcode1==0 &&tipcommand2.compareTo(")")==0){

         int tip_right_bracket=0;

         for(int i=0;i<tip_i;i++){if(Tipcommand[i].compareTo("(")==0)tip_right_bracket++;if(Tipcommand[i].compareTo(")")==0)tip_right_bracket--;}

         if(tip_right_bracket==0){Tipcode1=10;}

         }

         //检测输入=的合法性

         if(Tipcode1==0 &&tipcommand2.compareTo("=")==0){

         int tip_bracket=0;

         for(int i=0;i<tip_i;i++){if(Tipcommand[i].compareTo("(")==0){tip_bracket++;}if(Tipcommand[i].compareTo(")")==0){tip_bracket--;}}

         //若大于0,表明左括号还有未比配的

         if(tip_bracket>0){Tipcode1=9;bracket=tip_bracket;}

         //若前一个字符是以下之一,表明=不合法

         else if(tip_bracket==0){if("^sincostanlnlogn!".indexOf(tipcommand1)!=-1){Tipcode1=6;}

         if("+-×÷".indexOf(tipcommand1)!=-1){Tipcode1=5;}}           

         }

         //显示帮助和错误信息

         TipShow(bracket,Tipcode1,Tipcode2,tipcommand1,tipcommand2);

     }//private void TipChecker(String tipcommand1,String tipcommand2){}

2、计算部分的代码

 

 

 public void process(String str) {

                    int weightPlus = 0, topOp = 0,

                    topNum = 0, flag = 1, weightTemp = 0;

                    //weightPlus为同一()下的基本优先级,weightTemp临时记录优先级的变化

                    //topOp为weight[],operator[]的计数器;topNum为number[]的计数器

                    //flag为正负数的计数器,1为正数,-1为负数

                    int weight[];  //保存operator栈中运算符的优先级,以topOp计数

                    double number[];  //保存数字,以topNum计数

                    char ch, ch_gai, operator[];//operator[]保存运算符,以topOp计数

                    String num;//记录数字,str以+-×÷()sctgl!√^分段,+-×÷()sctgl!√^字符之间的字符串即为数字

                    weight = new int[MAXLEN];

                    number = new double[MAXLEN];

                    operator = new char[MAXLEN];

                    String expression = str;

                    StringTokenizer expToken = new StringTokenizer(expression,"+-×÷()sctgl!√^");

                    int i = 0;

                    while (i < expression.length()) {

                        ch = expression.charAt(i);

                        //判断正负数

                        if (i == 0) {

                            if (ch == '-')

                             flag = -1;

                        } else if(expression.charAt(i-1) == '(' && ch == '-')

                         flag = -1;

                        //取得数字,并将正负符号转移给数字

                        if (ch <= '9' && ch >= '0'|| ch == '.' || ch == 'E') {

                            num = expToken.nextToken();

                            ch_gai = ch;

                            Log.e("guojs",ch+"--->"+i);

                            //取得整个数字

                            while (i < expression.length() && 

                                    (ch_gai <= '9' && ch_gai >= '0'|| ch_gai == '.' || ch_gai == 'E')) 

                            {

                                ch_gai = expression.charAt(i++);

                                Log.e("guojs","i的值为:"+i);

                            }

                            //将指针退回之前的位置

                            if (i >= expression.length()) i-=1; else {i-=2;}

                            if (num.compareTo(".") == 0) number[topNum++] = 0;

                            //将正负符号转移给数字

                            else {

                                number[topNum++] = Double.parseDouble(num)*flag;

                                flag = 1;

                            }

                        }

                        //计算运算符的优先级

                        if (ch == '(') weightPlus+=4;

                        if (ch == ')') weightPlus-=4;

                        if (ch == '-' && flag == 1 || ch == '+' || ch == '×'|| ch == '÷' || 

                                ch == 's' ||ch == 'c' || ch == 't' || ch == 'g' || ch == 'l' || 

                                ch == '!' || ch == '√' || ch == '^') {

                            switch (ch) {

                             //+-的优先级最低,为1

                                case '+':

                                case '-':

                                    weightTemp = 1 + weightPlus;

                                    break;

                                //x÷的优先级稍高,为2

                                case '×':

                                case '÷':

                                    weightTemp = 2 + weightPlus;

                                    break;

                                //sincos之类优先级为3

                                case 's':

                                case 'c':

                                case 't':

                                case 'g':

                                case 'l':

                                case '!':

                                    weightTemp = 3 + weightPlus;

                                    break;

                                //其余优先级为4

                                //case '^':

                                //case '√':

                                default:

                                    weightTemp = 4 + weightPlus;

                                    break;

                            }

                            //如果当前优先级大于堆栈顶部元素,则直接入栈

                            if (topOp == 0 || weight[topOp-1] < weightTemp) {

                                weight[topOp] = weightTemp;

                                operator[topOp] = ch;

                                topOp++;

                            //否则将堆栈中运算符逐个取出,直到当前堆栈顶部运算符的优先级小于当前运算符

                            }else {

                                 while (topOp > 0 && weight[topOp-1] >= weightTemp) {

                                    switch (operator[topOp-1]) {

                                     //取出数字数组的相应元素进行运算

                                        case '+':

                                            number[topNum-2]+=number[topNum-1];

                                            break;

                                        case '-':

                                            number[topNum-2]-=number[topNum-1];

                                            break;

                                        case '×':

                                            number[topNum-2]*=number[topNum-1];

                                            break;

                                        //判断除数为0的情况

                                        case '÷':

                                            if (number[topNum-1] == 0) {

                                                showError(1,str_old);

                                                return;

                                            }

                                            number[topNum-2]/=number[topNum-1];

                                            break;

                                        case '√':

                                            if(number[topNum-1] == 0 || (number[topNum-2] < 0 &&

                                                    number[topNum-1] % 2 == 0)) {

                                                showError(2,str_old);

                                                return;    

                                            } 

                                            number[topNum-2] = 

                                                Math.pow(number[topNum-2], 1/number[topNum-1]);

                                            break;

                                        case '^':

                                            number[topNum-2] = 

                                                Math.pow(number[topNum-2], number[topNum-1]);

                                            break;

                                        //计算时进行角度弧度的判断及转换

                                        //sin

                                        case 's':

                                            if(drg_flag == true) {

                                                number[topNum-1] = Math.sin((number[topNum-1]/180)*pi);

                                            } else {

                                                number[topNum-1] = Math.sin(number[topNum-1]);

                                            }

                                            topNum++;

                                            break;

                                        //cos

                                        case 'c':

                                            if(drg_flag == true) {

                                                number[topNum-1] = Math.cos((number[topNum-1]/180)*pi);

                                            } else {

                                                number[topNum-1] = Math.cos(number[topNum-1]);

                                            }

                                            topNum++;

                                            break;

                                        //tan

                                        case 't':

                                            if(drg_flag == true) {

                                                if((Math.abs(number[topNum-1])/90)%2 == 1) {

                                                    showError(2,str_old);

                                                    return;

                                                }

                                                number[topNum-1] = Math.tan((number[topNum-1]/180)*pi);

                                            } else {

                                                if((Math.abs(number[topNum-1])/(pi/2))%2 == 1) {

                                                    showError(2,str_old);

                                                    return;

                                                }

                                                number[topNum-1] = Math.tan(number[topNum-1]);

                                            }

                                            topNum++;

                                            break;

                                        //log

                                        case 'g':

                                            if(number[topNum-1] <= 0) {

                                                showError(2,str_old);

                                                return;    

                                            } 

                                            number[topNum-1] = Math.log10(number[topNum-1]);

                                            topNum++;

                                            break;

                                        //ln

                                        case 'l':

                                            if(number[topNum-1] <= 0) {

                                                showError(2,str_old);

                                                return;    

                                            } 

                                            number[topNum-1] = Math.log(number[topNum-1]);

                                            topNum++;

                                            break;

                                        //阶乘

                                        case '!':

                                            if(number[topNum-1] > 170) {

                                                showError(3,str_old);

                                                return;    

                                            } else if(number[topNum-1] < 0) {

                                                showError(2,str_old);

                                                return;

                                            }

                                            number[topNum-1] = N(number[topNum-1]);

                                            topNum++;

                                            break;

                                    }

                                    //继续取堆栈的下一个元素进行判断

                                    topNum--;

                                    topOp--;

                                }

                                //将运算符如堆栈

                                weight[topOp] = weightTemp;

                                operator[topOp] = ch;

                                topOp++;

                            }

                        }

                        i++;

                    }

                    

                    //依次取出堆栈的运算符进行运算

                    while (topOp>0) {

                     //+-x直接将数组的后两位数取出运算

                        switch (operator[topOp-1]) {

                        case '+':

                            number[topNum-2]+=number[topNum-1];

                            break;

                        case '-':

                            number[topNum-2]-=number[topNum-1];

                            break;

                        case '×':

                            number[topNum-2]*=number[topNum-1];

                            break;

                        //涉及到除法时要考虑除数不能为零的情况

                        case '÷':

                            if (number[topNum-1] == 0) {

                                showError(1,str_old);

                                return;

                            }

                            number[topNum-2]/=number[topNum-1];

                            break;

                        case '√':

                            if(number[topNum-1] == 0 || (number[topNum-2] < 0 &&

                                    number[topNum-1] % 2 == 0)) {

                                showError(2,str_old);

                                return;    

                            } 

                            number[topNum-2] = 

                                Math.pow(number[topNum-2], 1/number[topNum-1]);

                            break;

                        case '^':

                            number[topNum-2] = 

                                Math.pow(number[topNum-2], number[topNum-1]);

                            break;

                        //sin

                        case 's':

                            if(drg_flag == true) {

                                number[topNum-1] = Math.sin((number[topNum-1]/180)*pi);

                            } else {

                                number[topNum-1] = Math.sin(number[topNum-1]);

                            }

                            topNum++;

                            break;

                        //cos

                        case 'c':

                            if(drg_flag == true) {

                                number[topNum-1] = Math.cos((number[topNum-1]/180)*pi);

                            } else {

                                number[topNum-1] = Math.cos(number[topNum-1]);

                            }

                            topNum++;

                            break;

                        //tan

                        case 't':

                            if(drg_flag == true) {

                                if((Math.abs(number[topNum-1])/90)%2 == 1) {

                                    showError(2,str_old);

                                    return;

                                }

                                number[topNum-1] = Math.tan((number[topNum-1]/180)*pi);

                            } else {

                                if((Math.abs(number[topNum-1])/(pi/2))%2 == 1) {

                                    showError(2,str_old);

                                    return;

                                }

                                number[topNum-1] = Math.tan(number[topNum-1]);

                            }

                            topNum++;

                            break;

                        //对数log

                        case 'g':

                            if(number[topNum-1] <= 0) {

                                showError(2,str_old);

                                return;    

                            } 

                            number[topNum-1] = Math.log10(number[topNum-1]);

                            topNum++;

                            break;

                        //自然对数ln

                        case 'l':

                            if(number[topNum-1] <= 0) {

                                showError(2,str_old);

                                return;    

                            } 

                            number[topNum-1] = Math.log(number[topNum-1]);

                            topNum++;

                            break;

                        //阶乘

                        case '!':

                            if(number[topNum-1] > 170) {

                                showError(3,str_old);

                                return;    

                            } else if(number[topNum-1] < 0) {

                                showError(2,str_old);

                                return;

                            }

                            number[topNum-1] = N(number[topNum-1]);

                            topNum++;

                            break;

                        }

                        //取堆栈下一个元素计算

                        topNum--;

                        topOp--;

                    }

                    //如果是数字太大,提示错误信息

                    if(number[0] > 7.3E306) {

                        showError(3,str_old);

                        return;

                    }

                    //输出最终结果

                    input.setText(String.valueOf(FP(number[0]))); 

                    tip.setText("计算完毕,要继续请按归零键 C");

                    mem.setText(str_old+"="+String.valueOf(FP(number[0])));

                }

2.下周计划:蓝牙


0 0