1.3 运算符与表达式

基础知识

运算符是告诉编译器执行特定数学或逻辑操作的符号。表达式是运算符和操作数的组合,它会产生一个值。Dart 语言支持多种类型的运算符,包括算术运算符、关系运算符、类型测试运算符、赋值运算符、逻辑运算符、位运算符和条件运算符等。

1. 算术运算符

用于执行基本的数学运算。

运算符 描述 示例 结果
+ 加法 5 + 2 7
- 减法 5 - 2 3
* 乘法 5 * 2 10
/ 除法 5 / 2 2.5
~/ 整除 5 ~/ 2 2
% 取模 5 % 2 1
++ 自增 a++ (后增) a 先用后加
-- 自减 a-- (后减) a 先用后减

2. 关系运算符

用于比较两个操作数,并返回布尔值 truefalse

运算符 描述 示例 结果
== 等于 a == b truefalse
!= 不等于 a != b truefalse
> 大于 a > b truefalse
< 小于 a < b truefalse
>= 大于等于 a >= b truefalse
<= 小于等于 a <= b truefalse

3. 类型测试运算符

用于在运行时检查对象的类型。

运算符 描述 示例
is 如果对象是指定类型,则返回 true obj is String
is! 如果对象不是指定类型,则返回 true obj is! int
as 类型转换(类型转换失败会抛出异常) obj as String

4. 赋值运算符

用于给变量赋值。

运算符 描述 示例 等同于
= 赋值 a = 10
+= 加法赋值 a += 5 a = a + 5
-= 减法赋值 a -= 5 a = a - 5
*= 乘法赋值 a *= 5 a = a * 5
/= 除法赋值 a /= 5 a = a / 5
~/= 整除赋值 a ~/= 5 a = a ~/ 5
%= 取模赋值 a %= 5 a = a % 5
??= 空值赋值 a ??= 5 如果 anull,则 a = 5

5. 逻辑运算符

用于组合或修改布尔表达式。

运算符 描述 示例
&& 逻辑与 true && false (返回 false)
` `
! 逻辑非 !true (返回 false)

6. 位运算符

用于对整数的二进制位进行操作。

运算符 描述
& 按位与
` `
^ 按位异或
~ 按位取反
<< 左移
>> 右移

7. 条件运算符

Dart 提供了两种特殊的条件运算符:

  • 三元运算符 (condition ? expr1 : expr2):如果 conditiontrue,则返回 expr1 的值;否则返回 expr2 的值。
  • 空值合并运算符 (expr1 ?? expr2):如果 expr1 不为 null,则返回 expr1 的值;否则返回 expr2 的值。
dart
复制代码
// 三元运算符
int a = 10;
int b = 20;
int max = (a > b) ? a : b; // max = 20

// 空值合并运算符
String? name; // 可空类型
String displayName = name ?? 'Guest'; // 如果 name 为 null,则 displayName 为 'Guest'

8. 级联运算符 (..)

级联运算符允许您对同一个对象执行一系列操作。它避免了创建临时变量,使代码更简洁。

dart
复制代码
// 不使用级联运算符
var sb = StringBuffer();
sb.write('Hello');
sb.write(' ');
sb.write('World');
print(sb.toString()); // 输出: Hello World

// 使用级联运算符
var sb2 = StringBuffer()
  ..write('Hello')
  ..write(' ')
  ..write('World');
print(sb2.toString()); // 输出: Hello World

官方文档链接

Flutter 开发中的应用案例

运算符在 Flutter 开发中无处不在,它们是实现逻辑判断、数据计算和 UI 交互的基础。掌握各种运算符的用法对于编写高效和健壮的 Flutter 应用至关重要。

案例:一个简单的计算器应用

我们将创建一个简单的计算器应用,演示算术运算符、赋值运算符和条件运算符的应用。

dart
复制代码
import 'package:flutter/material.dart';

class CalculatorApp extends StatefulWidget {
  const CalculatorApp({super.key});

  @override
  State<CalculatorApp> createState() => _CalculatorAppState();
}

class _CalculatorAppState extends State<CalculatorApp> {
  String _output = '0';
  String _currentNumber = '';
  double _num1 = 0.0;
  double _num2 = 0.0;
  String _operator = '';
  bool _isOperatorPressed = false;

  void _buttonPressed(String buttonText) {
    if (buttonText == 'CLEAR') {
      _output = '0';
      _currentNumber = '';
      _num1 = 0.0;
      _num2 = 0.0;
      _operator = '';
      _isOperatorPressed = false;
    } else if (buttonText == '+' ||
        buttonText == '-' ||
        buttonText == '×' ||
        buttonText == '÷') {
      _num1 = double.parse(_output);
      _operator = buttonText;
      _isOperatorPressed = true;
      _currentNumber = ''; // 清空当前数字,准备输入下一个数字
    } else if (buttonText == '.') {
      if (_currentNumber.contains('.')) {
        return; // 已经包含小数点,不再添加
      }
      _currentNumber += buttonText;
    } else if (buttonText == '=') {
      _num2 = double.parse(_currentNumber);

      if (_operator == '+') {
        _output = (_num1 + _num2).toString();
      } else if (_operator == '-') {
        _output = (_num1 - _num2).toString();
      } else if (_operator == '×') {
        _output = (_num1 * _num2).toString();
      } else if (_operator == '÷') {
        // 使用条件运算符处理除数为零的情况
        _output = (_num2 != 0) ? (_num1 / _num2).toString() : 'Error';
      }

      _num1 = double.parse(_output); // 将结果作为第一个操作数,方便连续计算
      _operator = '';
      _currentNumber = _output; // 将结果显示在当前数字中
      _isOperatorPressed = false;
    } else {
      // 如果是数字键
      if (_output == '0' || _isOperatorPressed) {
        _output = buttonText;
        _isOperatorPressed = false;
      } else {
        _output += buttonText;
      }
      _currentNumber += buttonText;
    }

    setState(() {});
  }

  Widget _buildButton(String buttonText) {
    return Expanded(
      child: OutlinedButton(
        style: OutlinedButton.styleFrom(
          padding: const EdgeInsets.all(24.0),
        ),
        onPressed: () => _buttonPressed(buttonText),
        child: Text(
          buttonText,
          style: const TextStyle(fontSize: 20.0, fontWeight: FontWeight.bold),
        ),
      ),
    );
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('简易计算器'),
      ),
      body: Column(
        children: <Widget>[
          Container(
            alignment: Alignment.centerRight,
            padding: const EdgeInsets.symmetric(vertical: 24.0, horizontal: 12.0),
            child: Text(
              _output,
              style: const TextStyle(fontSize: 48.0, fontWeight: FontWeight.bold),
            ),
          ),
          const Expanded(child: Divider()),
          Column(
            children: <Widget>[
              Row(
                children: <Widget>[
                  _buildButton('7'),
                  _buildButton('8'),
                  _buildButton('9'),
                  _buildButton('÷'),
                ],
              ),
              Row(
                children: <Widget>[
                  _buildButton('4'),
                  _buildButton('5'),
                  _buildButton('6'),
                  _buildButton('×'),
                ],
              ),
              Row(
                children: <Widget>[
                  _buildButton('1'),
                  _buildButton('2'),
                  _buildButton('3'),
                  _buildButton('-'),
                ],
              ),
              Row(
                children: <Widget>[
                  _buildButton('.'),
                  _buildButton('0'),
                  _buildButton('CLEAR'),
                  _buildButton('+'),
                ],
              ),
              Row(
                children: <Widget>[
                  _buildButton('='),
                ],
              ),
            ],
          )
        ],
      ),
    );
  }
}

void main() {
  runApp(const MaterialApp(home: CalculatorApp()));
}

案例分析:

  • 算术运算符:在 _buttonPressed 方法中,根据 _operator 的值,使用了 +-*/ 等算术运算符进行计算。
  • 赋值运算符_output = (_num1 + _num2).toString(); 等语句使用了 = 赋值运算符。_output += buttonText; 则使用了 += 复合赋值运算符。
  • 关系运算符if (_num2 != 0) 中使用了 != 不等于运算符来判断除数是否为零,避免除零错误。
  • 条件运算符_output = (_num2 != 0) ? (_num1 / _num2).toString() : 'Error'; 这里使用了三元运算符,如果 _num2 不为零,则执行除法并转换为字符串;否则,将 _output 设置为 'Error'
  • 逻辑运算符else if (buttonText == '+' || buttonText == '-' || buttonText == '×' || buttonText == '÷') 中使用了 || 逻辑或运算符来判断按下的按钮是否为运算符。
  • 类型转换double.parse(_output)double.parse(_currentNumber) 将字符串转换为 double 类型进行计算。

这个计算器案例直观地展示了 Dart 中各种运算符在实际 Flutter 应用中的应用。通过这些运算符,我们可以实现复杂的逻辑和数据处理,从而构建功能丰富的用户界面。