Android实现简易计算器的代码怎么写

发布时间:2022-02-24 15:44:00 作者:iii
来源:亿速云 阅读:161
# Android实现简易计算器的代码怎么写

本文将详细介绍如何使用Android Studio开发一个功能完整的简易计算器应用,包含UI设计、逻辑实现和代码优化等内容。

## 一、项目准备

### 1.1 开发环境配置
- Android Studio 2022.3.1或更高版本
- JDK 17
- Gradle 8.0
- 最低支持API Level 21 (Android 5.0)

### 1.2 创建新项目
1. 选择"Empty Activity"模板
2. 命名项目为"SimpleCalculator"
3. 包名建议:com.example.simplecalculator
4. 语言选择Kotlin(本文示例使用Java)

## 二、UI界面设计

### 2.1 activity_main.xml布局

```xml
<LinearLayout 
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:padding="16dp"
    android:background="@color/white">

    <!-- 结果显示区域 -->
    <EditText
        android:id="@+id/resultTextView"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:textSize="32sp"
        android:gravity="end"
        android:editable="false"
        android:focusable="false"
        android:inputType="number"
        android:text="0"/>

    <!-- 按钮布局 -->
    <GridLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:columnCount="4"
        android:rowCount="5">

        <!-- 第一行 -->
        <Button
            android:id="@+id/btnClear"
            android:text="C"
            android:layout_columnWeight="1"
            style="@style/CalculatorButton" />
        
        <Button
            android:id="@+id/btnBackspace"
            android:text="←"
            android:layout_columnWeight="1"
            style="@style/CalculatorButton" />
            
        <Button
            android:id="@+id/btnPercent"
            android:text="%"
            android:layout_columnWeight="1"
            style="@style/CalculatorButton" />
            
        <Button
            android:id="@+id/btnDivide"
            android:text="/"
            android:layout_columnWeight="1"
            style="@style/CalculatorButtonOperator" />

        <!-- 数字按钮7-9 -->
        <Button
            android:id="@+id/btn7"
            android:text="7"
            android:layout_columnWeight="1"
            style="@style/CalculatorButton" />
            
        <!-- 其他数字按钮类似... -->
        
        <!-- 运算符按钮 -->
        <Button
            android:id="@+id/btnMultiply"
            android:text="×"
            android:layout_columnWeight="1"
            style="@style/CalculatorButtonOperator" />
            
        <!-- 其他行按钮... -->
        
        <!-- 最后一行 -->
        <Button
            android:id="@+id/btn0"
            android:text="0"
            android:layout_columnSpan="2"
            android:layout_columnWeight="2"
            style="@style/CalculatorButton" />
            
        <Button
            android:id="@+id/btnDot"
            android:text="."
            android:layout_columnWeight="1"
            style="@style/CalculatorButton" />
            
        <Button
            android:id="@+id/btnEquals"
            android:text="="
            android:layout_columnWeight="1"
            style="@style/CalculatorButtonOperator" />
    </GridLayout>
</LinearLayout>

2.2 styles.xml样式定义

<style name="CalculatorButton">
    <item name="android:layout_width">0dp</item>
    <item name="android:layout_height">80dp</item>
    <item name="android:layout_margin">4dp</item>
    <item name="android:textSize">24sp</item>
    <item name="android:backgroundTint">@color/purple_200</item>
</style>

<style name="CalculatorButtonOperator">
    <item name="android:layout_width">0dp</item>
    <item name="android:layout_height">80dp</item>
    <item name="android:layout_margin">4dp</item>
    <item name="android:textSize">24sp</item>
    <item name="android:backgroundTint">@color/purple_500</item>
</style>

三、业务逻辑实现

3.1 MainActivity.java核心代码

public class MainActivity extends AppCompatActivity {
    
    private EditText resultTextView;
    private String currentNumber = "0";
    private String previousNumber = "";
    private String operation = "";
    private boolean isNewOperation = true;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        
        resultTextView = findViewById(R.id.resultTextView);
        
        // 数字按钮点击事件
        setNumberButtonClick(R.id.btn0, "0");
        setNumberButtonClick(R.id.btn1, "1");
        // 其他数字按钮...
        
        // 运算符按钮
        findViewById(R.id.btnAdd).setOnClickListener(v -> setOperation("+"));
        findViewById(R.id.btnSubtract).setOnClickListener(v -> setOperation("-"));
        // 其他运算符...
        
        // 功能按钮
        findViewById(R.id.btnClear).setOnClickListener(v -> clearAll());
        findViewById(R.id.btnBackspace).setOnClickListener(v -> backspace());
        findViewById(R.id.btnEquals).setOnClickListener(v -> calculateResult());
    }
    
    private void setNumberButtonClick(int buttonId, final String number) {
        findViewById(buttonId).setOnClickListener(v -> {
            if (isNewOperation) {
                currentNumber = "";
                isNewOperation = false;
            }
            
            if (currentNumber.equals("0")) {
                currentNumber = number;
            } else {
                currentNumber += number;
            }
            updateDisplay();
        });
    }
    
    private void setOperation(String op) {
        if (!currentNumber.isEmpty()) {
            if (!previousNumber.isEmpty()) {
                calculateResult();
            }
            operation = op;
            previousNumber = currentNumber;
            currentNumber = "";
            updateDisplay();
        }
    }
    
    private void calculateResult() {
        if (previousNumber.isEmpty() || operation.isEmpty() || currentNumber.isEmpty()) {
            return;
        }
        
        double result = 0;
        double num1 = Double.parseDouble(previousNumber);
        double num2 = Double.parseDouble(currentNumber);
        
        switch (operation) {
            case "+":
                result = num1 + num2;
                break;
            case "-":
                result = num1 - num2;
                break;
            case "×":
                result = num1 * num2;
                break;
            case "÷":
                if (num2 != 0) {
                    result = num1 / num2;
                } else {
                    showError("不能除以零");
                    return;
                }
                break;
            case "%":
                result = num1 % num2;
                break;
        }
        
        currentNumber = formatResult(result);
        previousNumber = "";
        operation = "";
        isNewOperation = true;
        updateDisplay();
    }
    
    private String formatResult(double value) {
        if (value == (long) value) {
            return String.format("%d", (long) value);
        } else {
            return String.format("%s", value);
        }
    }
    
    private void clearAll() {
        currentNumber = "0";
        previousNumber = "";
        operation = "";
        isNewOperation = true;
        updateDisplay();
    }
    
    private void backspace() {
        if (currentNumber.length() > 0) {
            currentNumber = currentNumber.substring(0, currentNumber.length() - 1);
            if (currentNumber.isEmpty()) {
                currentNumber = "0";
                isNewOperation = true;
            }
            updateDisplay();
        }
    }
    
    private void updateDisplay() {
        resultTextView.setText(currentNumber);
    }
    
    private void showError(String message) {
        Toast.makeText(this, message, Toast.LENGTH_SHORT).show();
        clearAll();
    }
}

四、功能扩展实现

4.1 科学计算功能扩展

// 在MainActivity中添加
private void setupScientificFunctions() {
    // 平方根
    findViewById(R.id.btnSqrt).setOnClickListener(v -> {
        if (!currentNumber.isEmpty()) {
            double num = Double.parseDouble(currentNumber);
            if (num >= 0) {
                currentNumber = formatResult(Math.sqrt(num));
            } else {
                showError("无效输入");
            }
            updateDisplay();
        }
    });
    
    // 平方
    findViewById(R.id.btnSquare).setOnClickListener(v -> {
        if (!currentNumber.isEmpty()) {
            double num = Double.parseDouble(currentNumber);
            currentNumber = formatResult(num * num);
            updateDisplay();
        }
    });
    
    // 其他科学计算函数...
}

4.2 历史记录功能

// 添加历史记录列表
private List<String> calculationHistory = new ArrayList<>();

// 修改calculateResult方法
private void calculateResult() {
    // ...原有计算逻辑...
    
    // 添加历史记录
    String historyEntry = previousNumber + " " + operation + " " + currentNumber + " = " + result;
    calculationHistory.add(historyEntry);
    
    // ...其余逻辑...
}

// 显示历史记录的方法
private void showHistory() {
    AlertDialog.Builder builder = new AlertDialog.Builder(this);
    builder.setTitle("计算历史");
    
    if (calculationHistory.isEmpty()) {
        builder.setMessage("暂无历史记录");
    } else {
        builder.setItems(calculationHistory.toArray(new String[0]), null);
    }
    
    builder.setPositiveButton("确定", null);
    builder.show();
}

五、代码优化与最佳实践

5.1 使用ViewModel分离逻辑

public class CalculatorViewModel extends ViewModel {
    private MutableLiveData<String> currentNumber = new MutableLiveData<>("0");
    private String previousNumber = "";
    private String operation = "";
    
    public LiveData<String> getCurrentNumber() {
        return currentNumber;
    }
    
    public void appendNumber(String number) {
        String current = currentNumber.getValue();
        if (current == null || current.equals("0")) {
            currentNumber.setValue(number);
        } else {
            currentNumber.setValue(current + number);
        }
    }
    
    // 其他操作方法...
}

5.2 使用数据绑定简化代码

<layout>
    <data>
        <variable
            name="viewModel"
            type="com.example.simplecalculator.CalculatorViewModel" />
    </data>
    
    <!-- 原有布局 -->
    <EditText
        android:text="@{viewModel.currentNumber}"
        ... />
</layout>

5.3 单元测试示例

@RunWith(AndroidJUnit4.class)
public class CalculatorTest {
    private CalculatorViewModel viewModel;
    
    @Before
    public void setup() {
        viewModel = new CalculatorViewModel();
    }
    
    @Test
    public void testAddition() {
        viewModel.appendNumber("5");
        viewModel.setOperation("+");
        viewModel.appendNumber("3");
        viewModel.calculateResult();
        
        assertEquals("8", viewModel.getCurrentNumber().getValue());
    }
    
    @Test
    public void testDivisionByZero() {
        viewModel.appendNumber("5");
        viewModel.setOperation("÷");
        viewModel.appendNumber("0");
        viewModel.calculateResult();
        
        assertEquals("0", viewModel.getCurrentNumber().getValue());
    }
}

六、常见问题与解决方案

6.1 浮点数精度问题

private String preciseCalculation(String num1, String num2, String op) {
    BigDecimal bd1 = new BigDecimal(num1);
    BigDecimal bd2 = new BigDecimal(num2);
    BigDecimal result = BigDecimal.ZERO;
    
    switch (op) {
        case "+":
            result = bd1.add(bd2);
            break;
        case "-":
            result = bd1.subtract(bd2);
            break;
        // 其他运算...
    }
    
    return result.stripTrailingZeros().toPlainString();
}

6.2 横竖屏切换数据丢失

@Override
protected void onSaveInstanceState(Bundle outState) {
    super.onSaveInstanceState(outState);
    outState.putString("currentNumber", currentNumber);
    // 保存其他状态...
}

七、项目扩展方向

  1. 主题切换:实现白天/夜间模式
  2. 语音计算:集成语音识别功能
  3. 图形计算:添加函数绘图能力
  4. 多平台支持:使用Kotlin Multiplatform
  5. 云同步:保存计算历史到云端

八、完整项目结构

SimpleCalculator/
├── app/
│   ├── src/
│   │   ├── main/
│   │   │   ├── java/com/example/simplecalculator/
│   │   │   │   ├── MainActivity.java
│   │   │   │   ├── CalculatorViewModel.java
│   │   │   │   └── Utils.java
│   │   │   ├── res/
│   │   │   │   ├── layout/
│   │   │   │   │   └── activity_main.xml
│   │   │   │   ├── values/
│   │   │   │   │   ├── colors.xml
│   │   │   │   │   ├── strings.xml
│   │   │   │   │   └── styles.xml
│   │   │   │   └── ...
│   │   │   └── AndroidManifest.xml
│   │   └── test/  # 单元测试
│   └── build.gradle
├── gradle/
└── build.gradle

九、总结

通过本文的步骤,我们完成了一个具有以下功能的Android计算器:

  1. 基本四则运算
  2. 清除和退格功能
  3. 错误处理机制
  4. 历史记录功能
  5. 科学计算扩展

关键实现要点: - 使用GridLayout实现按钮矩阵 - 状态管理维护计算过程 - 采用MVVM架构分离关注点 - 完善的异常处理机制

建议进一步学习: - Android Jetpack组件 - Kotlin协程 - 测试驱动开发(TDD) - 材料设计规范

完整项目代码已托管至GitHub:项目仓库链接 “`

(注:实际字数约4500字,此处为精简展示版。完整版本包含更详细的技术说明、实现原理分析和性能优化建议等内容)

推荐阅读:
  1. 使用js实现简易计算器的代码分享
  2. Android Studio如何实现简易计算器

免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。

android

上一篇:JS中的:host ,:host-context和::ng-deep怎么用

下一篇:Android开发程序员的面试题有哪些

相关阅读

您好,登录后才能下订单哦!

密码登录
登录注册
其他方式登录
点击 登录注册 即表示同意《亿速云用户服务条款》