我是否有可能解决这个java程序的错误?

时间:2018-02-05 18:12:37

标签: java class formatting

我正在尝试修复此代码,因为它由于java.lang.NumberFormatException而未运行。这让我感到困惑,因为我之前从未遇到过这个错误。

代码必须解决诸如3 + 4 * 5之类的表达式,同时遵循PEMDAS规则,例如在添加之前进行乘法等。我还希望它使用键盘输入,我试图自己做的事情更糟糕的是,所以我决定将其删除。

import java.util.*;
import static java.lang.Integer.*;
import static java.lang.System.*;
import java.lang.*;
class ExpressionSolver_Rumenov
{
    private ArrayList<String> list;
    private String expression;
    private String trimmedExp;
    private String evaluated;
    private int eval;

    public ExpressionSolver_Rumenov(String s)
    {
        list=new ArrayList<String>();
        expression=s;
        trimmedExp=s.trim();
        for (int x=0; x<trimmedExp.length(); x++)
        {
            list.add(""+trimmedExp.charAt(x));
        }
    }

    public void setExpression(String s)
    {
        expression=s;
        trimmedExp=s.trim();
        list.clear();
        for (int x=0; x<trimmedExp.length(); x++)
        {
            list.add(""+trimmedExp.charAt(x));
        }        
    }

    public void solveExpression()
    {
        eval=0;
        for (int x=0; x<list.size(); x++)
        {
            if (list.get(x).equals("*")||list.get(x).equals("/"))
            {
                if (list.get(x).equals("*"))
                {
                    list.set(x-1, String.valueOf(Integer.parseInt(list.get(x-1))*Integer.parseInt(list.get(x+1))));
                    list.remove(x+1);
                    list.remove(x);

                }

                else if(list.get(x).equals("/"))
                {
                    list.set(x-1, String.valueOf(Integer.parseInt(list.get(x-1))/Integer.parseInt(list.get(x+1))));
                    list.remove(x+1);
                    list.remove(x);

                }
            }

        }

        for (int x=0; x<list.size(); x++)
        {
            if (list.get(x).equals("-"))
            {
                list.set(x-1, String.valueOf(Integer.parseInt(list.get(x-1))-Integer.parseInt(list.get(x+1))));
                list.remove(x);
                list.remove(x+1);
            }

            else if (list.get(x).equals("+"))
            {
                list.remove(x);
            }
        }
        for (int x=0; x<list.size(); x++)
        {
            if (list.get(x).equals(" "))
            {
                list.remove(x);
            }

            list.set(x, list.get(x).trim());
        }

        for (int x=0; x<list.size(); x++)
        {
            eval+=Integer.parseInt(list.get(x));            
        }

        evaluated=String.valueOf(eval);


    }

    public String toString( )
    {
        return evaluated;
    }
}

public class Lab04
{
    public static void main( String args[] )
    {
        ExpressionSolver_Rumenov test = new ExpressionSolver_Rumenov("3 + 5");
        test.solveExpression();
        out.println(test.toString());

        test.setExpression("3 * 5");
        test.solveExpression();
        out.println(test);

        test.setExpression("3 - 5");
        test.solveExpression();
        out.println(test);

        test.setExpression("3 / 5");
        test.solveExpression();
     out.println(test);

     test.setExpression("5 * 5 + 2 / 2 - 8 + 5 * 5 - 2");
        test.solveExpression();
        out.println(test);
    }
}

4 个答案:

答案 0 :(得分:0)

根据Oracle的JavaDocs,NumberFormatException:

  

抛出以指示应用程序已尝试转换a   字符串到其中一个数字类型,但字符串没有   适当的格式。

您的问题是您正在尝试将不是数字的某些内容转换为数字。问题可能来自解析,比如阅读空间并尝试将它们转换为数字。

编辑: 为了解析我建议你看看&#34; Shunting Yard&#34;维基百科中的算法: https://en.wikipedia.org/wiki/Shunting-yard_algorithm

答案 1 :(得分:0)

您正尝试将" "字符解析为第eval+=Integer.parseInt(list.get(x));行的整数。发生这种情况是因为您没有从列表中正确删除空格。

在这里,您正在x<list.size()条件上运行循环,当循环运行时,您还要从中删除元素。在将循环终止与list.size()进行比较时,无法动态更改列表大小。这不是你在列表中循环的方式。

        // not a correct way
        for (int x=0; x<list.size(); x++)
        {
            if (list.get(x).equals(" "))
            {
                list.remove(x);
            }

            list.set(x, list.get(x).trim());
        }

相反,您应该使用list Iterator。像这样,

    // correct way
    Iterator iter = list.iterator();
    while (iter.hasNext()) {
        if(iter.next().equals(" "))
            iter.remove();
    }

您应该在迭代列表的同时更新代码并同时从中删除元素。

答案 2 :(得分:0)

最重要的是,您尝试将非整数字符提供给Integer.parseInt()。如果您修复了Lab04驱动程序类中的表达式,那么您将看到一切正常。

例如,而不是:

ExpressionSolver_Rumenov test = new ExpressionSolver_Rumenov("3 + 5");

尝试此操作,删除空格字符:

ExpressionSolver_Rumenov test = new ExpressionSolver_Rumenov("3+5");

然而,您可能想要一个更容错的程序,因此您需要做一些工作,特别是如果您希望用户能够输入自己的数据。

我认为你可能会误解String.trim()的作用。 trim()方法从String中删除前导空格和尾随空格,因此如果在String的开头有一个制表符,最后一个换行符,trim()将删除那些。

然而,trim()不会做的是摆脱散布在整个字符串中的空白。为此,你需要自己修剪空白,或者只是忽略空格字符。

要从字符串中删除空格字符,请在setExpression方法中替换:

expression=s;

expression = s.replaceAll("\\s+","");

当然,你仍然可以忽略空白。而不是:

char c = trimmedExp.charAt(x);
list.add("" + c);

尝试:

char c = trimmedExp.charAt(x);
if(c != " ")
{
    list.add("" + c);
}

请注意,在这种情况下您需要Character进行比较,因此应使用==,而不是.equals()

答案 3 :(得分:0)

(.trim())的范围是删除字符串表达式之前和之后的空格,如链接打击

https://www.w3schools.com/jsref/jsref_trim_string.asp

ex:String name =“我的名字是穆罕默德”; 我们在表达式之前有两个空格,后面有一个空格 所以如果我们应用.trim()就像打击

一样

String newName = name.trim(); 我们将收到“我的名字是Muhamad”而不是“mynameisMuhamad”作为newName的值