【问题标题】:Calculator with single edittext field具有单个编辑文本字段的计算器
【发布时间】:2015-12-27 18:59:32
【问题描述】:

我是 android 开发新手,我正在尝试开发一个带有单个编辑文本字段的计算器。它没有显示任何编译器错误,但只要我按下任何按钮,它就会崩溃。我首先输入 num1 并清除编辑文本字段,然后使用 switch case 来检测操作并收集第二个数字的数据。

public class MainActivity extends Activity implements OnClickListener{

    EditText ino;

    Button btnadd;
    Button btnsub;
    Button btnmult;
    Button btndiv;
    Button btneq;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        ino=(EditText) findViewById(R.id.ino);

        btnadd=(Button) findViewById(R.id.add);
        btndiv=(Button) findViewById(R.id.div);
        btnsub=(Button) findViewById(R.id.sub);
        btnmult=(Button) findViewById(R.id.mult);
        btneq=(Button) findViewById(R.id.eq);

        btnadd.setOnClickListener((OnClickListener) this);
        btnsub.setOnClickListener(this);
        btnmult.setOnClickListener(this);
        btndiv.setOnClickListener(this);

    }

    @Override
    public void onClick(View v)
    {

        float num1=0,num2=0,res=0;
        String xyz="",ans;
        num1=Float.parseFloat(ino.getText().toString());

        ino.setText(xyz);
        switch(v.getId())
        {
            case R.id.add:

                num2=Float.parseFloat(ino.getText().toString());

                res=num2+num1;

                ans=Float.toString(res);

                break;
            case R.id.div:
                num2=Float.parseFloat(ino.getText().toString());
                ino.setText(xyz);
                res=num1/num2;

                ans=Float.toString(res);
                ino.setText(ans);
                break;
            case R.id.mult:
                num2=Float.parseFloat(ino.getText().toString());
                ino.setText(xyz);
                res=num2*num1;

                ans=Float.toString(res);
                ino.setText(ans);
                break;
            case R.id.sub:
                num2=Float.parseFloat(ino.getText().toString());
                ino.setText(xyz);
                res=num1-num2;

                ans=Float.toString(res);
                ino.setText(ans);
                break;
            case R.id.eq:
                ans=Float.toString(res);
                ino.setText(ans);
                break;
            default: break;
        }



    }
}

这是堆栈跟踪的副本。

 12-28 00:49:52.646 2125-2125/com.example.rishabh.calculator2
 E/AndroidRuntime: FATAL EXCEPTION: main
    Process: com.example.rishabh.calculator2, PID: 2125
    java.lang.NumberFormatException: Invalid float: ""
        at java.lang.StringToReal.invalidReal(StringToReal.java:63)
        at java.lang.StringToReal.parseFloat(StringToReal.java:308)
        at java.lang.Float.parseFloat(Float.java:306)
        at com.example.rishabh.calculator2.MainActivity.onClick(MainActivity.java:56)
        at android.view.View.performClick(View.java:5198)
        at android.view.View$PerformClick.run(View.java:21147)
        at android.os.Handler.handleCallback(Handler.java:739)
        at android.os.Handler.dispatchMessage(Handler.java:95)
        at android.os.Looper.loop(Looper.java:148)
        at android.app.ActivityThread.main(ActivityThread.java:5417)
        at java.lang.reflect.Method.invoke(Native Method)
        at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:726)
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:616)

【问题讨论】:

  • 请您添加一份您在问题崩溃时获得的堆栈跟踪的副本。
  • @Jahnold 添加了堆栈跟踪的副本。
  • 好吧,你应该只添加检查 ino.getText().toString().length > 0

标签: java android parsefloat


【解决方案1】:

您的代码包含几个问题。第一个是Float.parseFloat() 将在字符串为空或包含字母时抛出java.lang.NumberFormatException。这应该使用 try/catch 来处理。

第二个问题是变量num1num2res不能在本地声明,因为每次点击按钮都会初始化为0.0

为了使计算器工作,必须记住用户单击“等于”按钮时将要执行的操作。可以使用int 存储上一次单击的按钮。

以下代码已经过测试并且可以工作。

import android.app.Activity;
import android.os.Bundle;
import android.widget.Button;
import android.widget.EditText;
import android.view.View.*;
import android.view.View;

public class MainActivity extends Activity implements OnClickListener {

    EditText ino;

    Button btnadd;
    Button btnsub;
    Button btnmult;
    Button btndiv;
    Button btneq;

    private float num1 = 0;
    private float num2 = 0;
    private float res = 0;

    private int operation = 0;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        ino=(EditText) findViewById(R.id.ino);

        btnadd=(Button) findViewById(R.id.add);
        btndiv=(Button) findViewById(R.id.div);
        btnsub=(Button) findViewById(R.id.sub);
        btnmult=(Button) findViewById(R.id.mult);
        btneq=(Button) findViewById(R.id.eq);

        btnadd.setOnClickListener(this);
        btnsub.setOnClickListener(this);
        btnmult.setOnClickListener(this);
        btndiv.setOnClickListener(this);
        btneq.setOnClickListener(this);
    }

    @Override
    public void onClick(View v)
    {
        String s = ino.getText().toString();
        try
        {
            Float.parseFloat(s);
        }
        catch (NumberFormatException e)
        {
            s = "0.0";
        }

        String xyz="",ans;
        ino.setText(xyz);

        switch(v.getId())
        {
            case R.id.eq:
                num1=Float.parseFloat(s);

                switch (operation) {
                    case R.id.add:
                        res = num2 + num1;
                        break;
                    case R.id.sub:
                        res = num2 - num1;
                        break;
                    case R.id.mult:
                        res = num2 * num1;
                        break;
                    case R.id.div:
                        res = num2 / num1;
                        break;
                    default:
                        res = 0;
                        break;
                }
                ans=Float.toString(res);
                ino.setText(ans);
                break;
        }
        num2 = Float.parseFloat(s);
        operation = v.getId();
    }
}

【讨论】:

    【解决方案2】:

    从您的代码中可以清楚地看出它会抛出java.lang.NumberFormatException 异常。如果编辑文本包含无效字符串或空字符串parseFloat method will throw a NumberFormatException

    您在以下代码中将编辑文本值设置为空字符串(其中xyz 被初始化为空字符串):

    ino.setText(xyz);
    

    之后,您尝试将编辑文本数据解析为浮动,它将引发异常。您需要捕获这些异常并在代码中正确处理它。

    try
    {
       num1=Float.parseFloat(ino.getText().toString());
    }
    catch (NumberFormatException e)
    {
       num1 = 0.0f;
    }
    

    (类似这样,你需要处理所有的 parseFloat 调用)

    【讨论】:

      【解决方案3】:

      在您的 LogCat 中,我看到以下内容:

      java.lang.NumberFormatException: Invalid float: "" at java.lang.StringToReal.invalidReal(StringToReal.java:63)

      在您的代码中,您多次尝试解析字符串值并将其存储为浮点数,但这是行不通的:

      num1=Float.parseFloat(ino.getText().toString());
      

      相反,您应该使用以下方法将字符串转换为浮点数:

      num1 = Float.valueOf(ino.getText().toString());
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2017-07-25
        • 1970-01-01
        • 1970-01-01
        • 2020-08-13
        • 2012-10-09
        • 2020-07-24
        • 2013-08-18
        • 1970-01-01
        相关资源
        最近更新 更多