Dart 运算符和操作符详细总结

Dart 运算符和操作符详细总结

基于Dart官方API文档与实践经验整理

目录

概述

Dart提供了丰富的运算符集合,用于执行各种操作。运算符本质上是具有特殊语法的方法,大多数运算符都可以被重载。

核心特性

  • 丰富的运算符集合:涵盖算术、比较、逻辑、位操作等
  • 运算符重载:可以为自定义类定义运算符行为
  • 空安全运算符:支持空安全的运算符(??、??=、?.等)
  • 级联运算符:允许在同一对象上执行多个操作
  • 类型运算符:用于类型检查和转换
  • 优先级明确:清晰的运算符优先级和结合性规则

运算符分类

dart 复制代码
// 算术运算符
int sum = 5 + 3;        // 加法
int diff = 10 - 4;      // 减法
int product = 6 * 7;    // 乘法
double quotient = 15 / 4; // 除法

// 比较运算符
bool isEqual = (5 == 5);    // 相等
bool isGreater = (10 > 5);  // 大于

// 逻辑运算符
bool result = true && false;  // 逻辑与
bool result2 = true || false; // 逻辑或

// 赋值运算符
int x = 10;    // 赋值
x += 5;        // 复合赋值

// 条件运算符
String name = user?.name ?? 'Unknown';  // 空合并

// 级联运算符
list..add(1)..add(2)..sort();  // 级联调用

算术运算符

1. 基本算术运算符

dart 复制代码
void demonstrateArithmeticOperators() {
  int a = 10, b = 3;
  double x = 10.5, y = 3.2;
  
  // 加法 (+)
  print('$a + $b = ${a + b}');        // 10 + 3 = 13
  print('$x + $y = ${x + y}');        // 10.5 + 3.2 = 13.7
  
  // 减法 (-)
  print('$a - $b = ${a - b}');        // 10 - 3 = 7
  print('$x - $y = ${x - y}');        // 10.5 - 3.2 = 7.3
  
  // 乘法 (*)
  print('$a * $b = ${a * b}');        // 10 * 3 = 30
  print('$x * $y = ${x * y}');        // 10.5 * 3.2 = 33.6
  
  // 除法 (/)
  print('$a / $b = ${a / b}');        // 10 / 3 = 3.3333333333333335
  print('$x / $y = ${x / y}');        // 10.5 / 3.2 = 3.28125
  
  // 整除 (~/)
  print('$a ~/ $b = ${a ~/ b}');      // 10 ~/ 3 = 3
  print('${x.toInt()} ~/ ${y.toInt()} = ${x.toInt() ~/ y.toInt()}'); // 10 ~/ 3 = 3
  
  // 取模 (%)
  print('$a % $b = ${a % b}');        // 10 % 3 = 1
  print('$x % $y = ${x % y}');        // 10.5 % 3.2 = 0.8999999999999995
}

2. 一元算术运算符

dart 复制代码
void demonstrateUnaryOperators() {
  int number = 5;
  double decimal = 3.14;
  
  // 一元加号 (+)
  print('+$number = ${+number}');     // +5 = 5
  print('+$decimal = ${+decimal}');   // +3.14 = 3.14
  
  // 一元减号 (-)
  print('-$number = ${-number}');     // -5 = -5
  print('-$decimal = ${-decimal}');   // -3.14 = -3.14
  
  // 前置递增 (++var)
  int a = 10;
  print('++a: ${++a}');               // ++a: 11 (a现在是11)
  
  // 后置递增 (var++)
  int b = 10;
  print('b++: ${b++}');               // b++: 10 (b现在是11)
  print('b现在是: $b');                // b现在是: 11
  
  // 前置递减 (--var)
  int c = 10;
  print('--c: ${--c}');               // --c: 9 (c现在是9)
  
  // 后置递减 (var--)
  int d = 10;
  print('d--: ${d--}');               // d--: 10 (d现在是9)
  print('d现在是: $d');                // d现在是: 9
}

3. 算术运算符的特殊情况

dart 复制代码
void demonstrateSpecialCases() {
  // 整数溢出
  int maxInt = 9223372036854775807; // 64位系统的最大int值
  print('maxInt + 1 = ${maxInt + 1}'); // 溢出,结果为负数
  
  // 浮点数特殊值
  double positive = 1.0;
  double negative = -1.0;
  double zero = 0.0;
  
  print('1.0 / 0.0 = ${positive / zero}');     // Infinity
  print('-1.0 / 0.0 = ${negative / zero}');    // -Infinity
  print('0.0 / 0.0 = ${zero / zero}');         // NaN
  
  // 检查特殊值
  double inf = double.infinity;
  double nan = double.nan;
  
  print('isInfinite: ${inf.isInfinite}');      // true
  print('isNaN: ${nan.isNaN}');                // true
  print('isFinite: ${(3.14).isFinite}');      // true
  
  // 精度问题
  double result = 0.1 + 0.2;
  print('0.1 + 0.2 = $result');               // 0.30000000000000004
  print('0.1 + 0.2 == 0.3: ${result == 0.3}'); // false
  
  // 正确的浮点数比较
  bool isEqual = (result - 0.3).abs() < 1e-10;
  print('近似相等: $isEqual');                  // true
}

4. 字符串和列表的算术运算

dart 复制代码
void demonstrateStringListArithmetic() {
  // 字符串连接
  String firstName = 'John';
  String lastName = 'Doe';
  String fullName = firstName + ' ' + lastName;
  print('全名: $fullName');                    // 全名: John Doe
  
  // 字符串重复
  String star = '*';
  String stars = star * 5;
  print('星号: $stars');                       // 星号: *****
  
  // 列表连接
  List<int> list1 = [1, 2, 3];
  List<int> list2 = [4, 5, 6];
  List<int> combined = list1 + list2;
  print('合并列表: $combined');                // 合并列表: [1, 2, 3, 4, 5, 6]
  
  // 注意:不能对列表使用乘法运算符
  // List<int> repeated = list1 * 3; // 编译错误
  
  // 但可以通过其他方式实现重复
  List<int> repeated = [];
  for (int i = 0; i < 3; i++) {
    repeated.addAll(list1);
  }
  print('重复列表: $repeated');                // 重复列表: [1, 2, 3, 1, 2, 3, 1, 2, 3]
}

比较运算符

1. 相等性运算符

dart 复制代码
void demonstrateEqualityOperators() {
  // 基本类型比较
  int a = 5;
  int b = 5;
  int c = 10;
  
  print('$a == $b: ${a == b}');        // 5 == 5: true
  print('$a != $c: ${a != c}');        // 5 != 10: true
  
  // 字符串比较
  String str1 = 'hello';
  String str2 = 'hello';
  String str3 = 'Hello';
  
  print("'$str1' == '$str2': ${str1 == str2}");  // 'hello' == 'hello': true
  print("'$str1' == '$str3': ${str1 == str3}");  // 'hello' == 'Hello': false
  
  // 对象比较
  List<int> list1 = [1, 2, 3];
  List<int> list2 = [1, 2, 3];
  List<int> list3 = list1;
  
  print('list1 == list2: ${list1 == list2}');    // true (内容相同)
  print('identical(list1, list2): ${identical(list1, list2)}'); // false (不同对象)
  print('identical(list1, list3): ${identical(list1, list3)}'); // true (同一对象)
  
  // 空值比较
  String? nullString = null;
  String? anotherNull = null;
  String? notNull = 'value';
  
  print('null == null: ${nullString == anotherNull}');     // true
  print('null == "value": ${nullString == notNull}');     // false
}

2. 关系运算符

dart 复制代码
void demonstrateRelationalOperators() {
  int x = 10;
  int y = 20;
  double a = 15.5;
  double b = 15.5;
  
  // 小于 (<)
  print('$x < $y: ${x < y}');          // 10 < 20: true
  print('$y < $x: ${y < x}');          // 20 < 10: false
  
  // 小于等于 (<=)
  print('$x <= $y: ${x <= y}');        // 10 <= 20: true
  print('$a <= $b: ${a <= b}');        // 15.5 <= 15.5: true
  
  // 大于 (>)
  print('$y > $x: ${y > x}');          // 20 > 10: true
  print('$x > $y: ${x > y}');          // 10 > 20: false
  
  // 大于等于 (>=)
  print('$y >= $x: ${y >= x}');        // 20 >= 10: true
  print('$a >= $b: ${a >= b}');        // 15.5 >= 15.5: true
  
  // 字符串比较(按字典序)
  String str1 = 'apple';
  String str2 = 'banana';
  String str3 = 'Apple';
  
  print("'$str1' < '$str2': ${str1.compareTo(str2) < 0}");    // true
  print("'$str1' > '$str3': ${str1.compareTo(str3) > 0}");    // true (小写字母ASCII值大)
  
  // 使用Comparable接口
  DateTime date1 = DateTime(2023, 1, 1);
  DateTime date2 = DateTime(2023, 12, 31);
  
  print('$date1 < $date2: ${date1.isBefore(date2)}');         // true
  print('$date2 > $date1: ${date2.isAfter(date1)}');          // true
}

3. 自定义类的比较

dart 复制代码
class Person implements Comparable<Person> {
  final String name;
  final int age;
  
  Person(this.name, this.age);
  
  @override
  int compareTo(Person other) {
    // 首先按年龄比较,然后按姓名比较
    int ageComparison = age.compareTo(other.age);
    if (ageComparison != 0) {
      return ageComparison;
    }
    return name.compareTo(other.name);
  }
  
  @override
  bool operator ==(Object other) =>
      identical(this, other) ||
      other is Person &&
      runtimeType == other.runtimeType &&
      name == other.name &&
      age == other.age;
  
  @override
  int get hashCode => Object.hash(name, age);
  
  // 重载比较运算符
  bool operator <(Person other) => compareTo(other) < 0;
  bool operator <=(Person other) => compareTo(other) <= 0;
  bool operator >(Person other) => compareTo(other) > 0;
  bool operator >=(Person other) => compareTo(other) >= 0;
  
  @override
  String toString() => 'Person(name: $name, age: $age)';
}

void demonstrateCustomComparison() {
  Person alice = Person('Alice', 25);
  Person bob = Person('Bob', 30);
  Person charlie = Person('Charlie', 25);
  
  print('$alice == $bob: ${alice == bob}');           // false
  print('$alice < $bob: ${alice < bob}');             // true (年龄小)
  print('$alice < $charlie: ${alice < charlie}');     // true (年龄相同,姓名字典序)
  
  // 排序
  List<Person> people = [bob, charlie, alice];
  people.sort();
  print('排序后: $people');
  // 排序后: [Person(name: Alice, age: 25), Person(name: Charlie, age: 25), Person(name: Bob, age: 30)]
}

逻辑运算符

1. 基本逻辑运算符

dart 复制代码
void demonstrateLogicalOperators() {
  bool a = true;
  bool b = false;
  bool c = true;
  
  // 逻辑与 (&&)
  print('$a && $b = ${a && b}');       // true && false = false
  print('$a && $c = ${a && c}');       // true && true = true
  
  // 逻辑或 (||)
  print('$a || $b = ${a || b}');       // true || false = true
  print('$b || false = ${b || false}'); // false || false = false
  
  // 逻辑非 (!)
  print('!$a = ${!a}');                // !true = false
  print('!$b = ${!b}');                // !false = true
  
  // 复合逻辑表达式
  bool result1 = a && b || c;          // (true && false) || true = true
  bool result2 = a && (b || c);        // true && (false || true) = true
  bool result3 = !(a && b);            // !(true && false) = true
  
  print('a && b || c = $result1');
  print('a && (b || c) = $result2');
  print('!(a && b) = $result3');
}

2. 短路求值

dart 复制代码
bool expensiveOperation() {
  print('执行昂贵的操作...');
  return true;
}

bool anotherExpensiveOperation() {
  print('执行另一个昂贵的操作...');
  return false;
}

void demonstrateShortCircuitEvaluation() {
  print('=== 逻辑与的短路求值 ===');
  bool result1 = false && expensiveOperation();
  print('结果: $result1'); // expensiveOperation()不会被调用
  
  bool result2 = true && expensiveOperation();
  print('结果: $result2'); // expensiveOperation()会被调用
  
  print('\n=== 逻辑或的短路求值 ===');
  bool result3 = true || anotherExpensiveOperation();
  print('结果: $result3'); // anotherExpensiveOperation()不会被调用
  
  bool result4 = false || anotherExpensiveOperation();
  print('结果: $result4'); // anotherExpensiveOperation()会被调用
}

3. 实际应用场景

dart 复制代码
class User {
  String? name;
  int? age;
  bool isActive;
  List<String> roles;
  
  User({this.name, this.age, this.isActive = false, this.roles = const []});
  
  bool get isValid => name != null && name!.isNotEmpty && age != null && age! > 0;
  bool get isAdmin => isActive && roles.contains('admin');
  bool get canEdit => isActive && (roles.contains('admin') || roles.contains('editor'));
}

void demonstrateLogicalInPractice() {
  User user1 = User(name: 'Alice', age: 25, isActive: true, roles: ['user']);
  User user2 = User(name: 'Bob', age: 30, isActive: true, roles: ['admin']);
  User user3 = User(name: '', age: -1, isActive: false);
  
  // 验证用户
  print('user1有效: ${user1.isValid}');      // true
  print('user3有效: ${user3.isValid}');      // false
  
  // 权限检查
  print('user1是管理员: ${user1.isAdmin}');   // false
  print('user2是管理员: ${user2.isAdmin}');   // true
  
  print('user1可编辑: ${user1.canEdit}');    // false
  print('user2可编辑: ${user2.canEdit}');    // true
  
  // 复杂条件
  bool canAccessAdminPanel = user2.isActive && 
                            user2.age != null && 
                            user2.age! >= 18 && 
                            (user2.roles.contains('admin') || user2.roles.contains('moderator'));
  
  print('user2可访问管理面板: $canAccessAdminPanel'); // true
}

4. 逻辑运算符与空安全

dart 复制代码
void demonstrateLogicalWithNullSafety() {
  String? nullableString = null;
  String? anotherString = 'hello';
  
  // 安全的逻辑运算
  bool result1 = nullableString != null && nullableString.isNotEmpty;
  print('nullableString不为空且不为空字符串: $result1'); // false
  
  bool result2 = anotherString != null && anotherString.isNotEmpty;
  print('anotherString不为空且不为空字符串: $result2'); // true
  
  // 使用空合并运算符
  bool result3 = (nullableString ?? '').isNotEmpty;
  print('使用空合并的结果: $result3'); // false
  
  // 组合使用
  bool isValidInput(String? input) {
    return input != null && 
           input.trim().isNotEmpty && 
           input.length >= 3;
  }
  
  print('isValidInput(null): ${isValidInput(null)}');           // false
  print('isValidInput(""): ${isValidInput("")}');               // false
  print('isValidInput("hi"): ${isValidInput("hi")}');           // false
  print('isValidInput("hello"): ${isValidInput("hello")}');     // true
}

位运算符

1. 基本位运算符

dart 复制代码
void demonstrateBitwiseOperators() {
  int a = 12;  // 二进制: 1100
  int b = 10;  // 二进制: 1010
  
  print('a = $a (${a.toRadixString(2).padLeft(8, '0')})');
  print('b = $b (${b.toRadixString(2).padLeft(8, '0')})');
  print('');
  
  // 按位与 (&)
  int andResult = a & b;  // 1100 & 1010 = 1000 (8)
  print('$a & $b = $andResult (${andResult.toRadixString(2).padLeft(8, '0')})');
  
  // 按位或 (|)
  int orResult = a | b;   // 1100 | 1010 = 1110 (14)
  print('$a | $b = $orResult (${orResult.toRadixString(2).padLeft(8, '0')})');
  
  // 按位异或 (^)
  int xorResult = a ^ b;  // 1100 ^ 1010 = 0110 (6)
  print('$a ^ $b = $xorResult (${xorResult.toRadixString(2).padLeft(8, '0')})');
  
  // 按位取反 (~)
  int notA = ~a;          // ~1100 = ...11110011 (取决于系统位数)
  print('~$a = $notA (${(notA & 0xFF).toRadixString(2).padLeft(8, '0')})');
  
  // 左移 (<<)
  int leftShift = a << 2; // 1100 << 2 = 110000 (48)
  print('$a << 2 = $leftShift (${leftShift.toRadixString(2).padLeft(8, '0')})');
  
  // 右移 (>>)
  int rightShift = a >> 2; // 1100 >> 2 = 11 (3)
  print('$a >> 2 = $rightShift (${rightShift.toRadixString(2).padLeft(8, '0')})');
}

2. 位运算的实际应用

dart 复制代码
// 权限系统使用位运算
class Permissions {
  static const int read = 1;      // 0001
  static const int write = 2;     // 0010
  static const int execute = 4;   // 0100
  static const int delete = 8;    // 1000
  
  int _permissions = 0;
  
  // 添加权限
  void grant(int permission) {
    _permissions |= permission;
  }
  
  // 撤销权限
  void revoke(int permission) {
    _permissions &= ~permission;
  }
  
  // 检查权限
  bool hasPermission(int permission) {
    return (_permissions & permission) == permission;
  }
  
  // 切换权限
  void toggle(int permission) {
    _permissions ^= permission;
  }
  
  // 获取所有权限
  int get permissions => _permissions;
  
  // 清除所有权限
  void clear() {
    _permissions = 0;
  }
  
  @override
  String toString() {
    List<String> perms = [];
    if (hasPermission(read)) perms.add('READ');
    if (hasPermission(write)) perms.add('WRITE');
    if (hasPermission(execute)) perms.add('EXECUTE');
    if (hasPermission(delete)) perms.add('DELETE');
    return perms.isEmpty ? 'NO_PERMISSIONS' : perms.join(', ');
  }
}

void demonstratePermissionSystem() {
  Permissions userPerms = Permissions();
  
  print('初始权限: $userPerms');
  
  // 授予读写权限
  userPerms.grant(Permissions.read | Permissions.write);
  print('授予读写权限后: $userPerms');
  
  // 检查权限
  print('有读权限: ${userPerms.hasPermission(Permissions.read)}');
  print('有删除权限: ${userPerms.hasPermission(Permissions.delete)}');
  
  // 添加执行权限
  userPerms.grant(Permissions.execute);
  print('添加执行权限后: $userPerms');
  
  // 撤销写权限
  userPerms.revoke(Permissions.write);
  print('撤销写权限后: $userPerms');
  
  // 切换删除权限
  userPerms.toggle(Permissions.delete);
  print('切换删除权限后: $userPerms');
  
  userPerms.toggle(Permissions.delete);
  print('再次切换删除权限后: $userPerms');
}

3. 位掩码和标志位

dart 复制代码
// 状态标志位示例
enum TaskStatus {
  pending,    // 0001
  running,    // 0010
  completed,  // 0100
  failed,     // 1000
}

class TaskManager {
  int _statusFlags = 0;
  
  void setStatus(TaskStatus status) {
    _statusFlags |= (1 << status.index);
  }
  
  void clearStatus(TaskStatus status) {
    _statusFlags &= ~(1 << status.index);
  }
  
  bool hasStatus(TaskStatus status) {
    return (_statusFlags & (1 << status.index)) != 0;
  }
  
  List<TaskStatus> get activeStatuses {
    List<TaskStatus> statuses = [];
    for (TaskStatus status in TaskStatus.values) {
      if (hasStatus(status)) {
        statuses.add(status);
      }
    }
    return statuses;
  }
  
  void reset() {
    _statusFlags = 0;
  }
}

void demonstrateBitFlags() {
  TaskManager manager = TaskManager();
  
  // 设置多个状态
  manager.setStatus(TaskStatus.pending);
  manager.setStatus(TaskStatus.running);
  
  print('当前状态: ${manager.activeStatuses}');
  
  // 检查状态
  print('是否待处理: ${manager.hasStatus(TaskStatus.pending)}');
  print('是否已完成: ${manager.hasStatus(TaskStatus.completed)}');
  
  // 更新状态
  manager.clearStatus(TaskStatus.pending);
  manager.setStatus(TaskStatus.completed);
  
  print('更新后状态: ${manager.activeStatuses}');
}

4. 位运算优化技巧

dart 复制代码
class BitTricks {
  // 检查数字是否为2的幂
  static bool isPowerOfTwo(int n) {
    return n > 0 && (n & (n - 1)) == 0;
  }
  
  // 计算数字中1的个数(汉明权重)
  static int countBits(int n) {
    int count = 0;
    while (n != 0) {
      count++;
      n &= (n - 1); // 清除最低位的1
    }
    return count;
  }
  
  // 交换两个数(不使用临时变量)
  static void swapNumbers(List<int> arr, int i, int j) {
    if (i != j) {
      arr[i] ^= arr[j];
      arr[j] ^= arr[i];
      arr[i] ^= arr[j];
    }
  }
  
  // 获取最低位的1
  static int getLowestBit(int n) {
    return n & (-n);
  }
  
  // 清除最低位的1
  static int clearLowestBit(int n) {
    return n & (n - 1);
  }
  
  // 设置第n位为1
  static int setBit(int number, int position) {
    return number | (1 << position);
  }
  
  // 清除第n位
  static int clearBit(int number, int position) {
    return number & ~(1 << position);
  }
  
  // 切换第n位
  static int toggleBit(int number, int position) {
    return number ^ (1 << position);
  }
  
  // 检查第n位是否为1
  static bool isBitSet(int number, int position) {
    return (number & (1 << position)) != 0;
  }
}

void demonstrateBitTricks() {
  // 测试2的幂
  List<int> numbers = [1, 2, 3, 4, 8, 15, 16, 32];
  for (int num in numbers) {
    print('$num 是2的幂: ${BitTricks.isPowerOfTwo(num)}');
  }
  
  // 计算位数
  int value = 42; // 101010
  print('$value 的二进制中有 ${BitTricks.countBits(value)} 个1');
  
  // 位操作
  int original = 10; // 1010
  print('原始值: $original (${original.toRadixString(2)})');
  
  int withBitSet = BitTricks.setBit(original, 0); // 设置第0位
  print('设置第0位后: $withBitSet (${withBitSet.toRadixString(2)})');
  
  int withBitCleared = BitTricks.clearBit(withBitSet, 1); // 清除第1位
  print('清除第1位后: $withBitCleared (${withBitCleared.toRadixString(2)})');
  
  int toggled = BitTricks.toggleBit(withBitCleared, 2); // 切换第2位
  print('切换第2位后: $toggled (${toggled.toRadixString(2)})');
}

赋值运算符

1. 基本赋值运算符

dart 复制代码
void demonstrateBasicAssignment() {
  // 简单赋值 (=)
  int a = 10;
  double b = 3.14;
  String c = 'Hello';
  bool d = true;
  
  print('a = $a, b = $b, c = $c, d = $d');
  
  // 多重赋值(通过元组或记录)
  (int x, int y) = (5, 10);
  print('x = $x, y = $y');
  
  // 列表赋值
  List<int> numbers = [1, 2, 3];
  List<String> names = ['Alice', 'Bob'];
  
  print('numbers = $numbers');
  print('names = $names');
  
  // 对象赋值
  Map<String, int> scores = {'Alice': 95, 'Bob': 87};
  print('scores = $scores');
}

2. 复合赋值运算符

dart 复制代码
void demonstrateCompoundAssignment() {
  int a = 10;
  double b = 5.5;
  String str = 'Hello';
  List<int> list = [1, 2, 3];
  
  print('初始值: a=$a, b=$b, str="$str", list=$list');
  
  // 算术复合赋值
  a += 5;        // a = a + 5
  print('a += 5: $a');
  
  a -= 3;        // a = a - 3
  print('a -= 3: $a');
  
  a *= 2;        // a = a * 2
  print('a *= 2: $a');
  
  b /= 2;        // b = b / 2
  print('b /= 2: $b');
  
  a ~/= 3;       // a = a ~/ 3 (整除)
  print('a ~/= 3: $a');
  
  int remainder = 17;
  remainder %= 5; // remainder = remainder % 5
  print('17 %= 5: $remainder');
  
  // 字符串复合赋值
  str += ' World';
  print('str += " World": "$str"');
  
  // 位运算复合赋值
  int flags = 12; // 1100
  flags &= 10;    // 1100 & 1010 = 1000
  print('flags &= 10: $flags (${flags.toRadixString(2)})');
  
  flags |= 3;     // 1000 | 0011 = 1011
  print('flags |= 3: $flags (${flags.toRadixString(2)})');
  
  flags ^= 7;     // 1011 ^ 0111 = 1100
  print('flags ^= 7: $flags (${flags.toRadixString(2)})');
  
  flags <<= 1;    // 1100 << 1 = 11000
  print('flags <<= 1: $flags (${flags.toRadixString(2)})');
  
  flags >>= 2;    // 11000 >> 2 = 110
  print('flags >>= 2: $flags (${flags.toRadixString(2)})');
}

3. 空赋值运算符

dart 复制代码
void demonstrateNullAssignment() {
  String? name;
  String? email;
  int? age;
  
  // 空合并赋值运算符 (??=)
  // 只有当变量为null时才赋值
  name ??= 'Default Name';
  print('name ??= "Default Name": $name');  // Default Name
  
  name ??= 'Another Name';
  print('name ??= "Another Name": $name');  // Default Name (不变)
  
  email ??= 'default@example.com';
  print('email ??= "default@example.com": $email');
  
  age ??= 18;
  print('age ??= 18: $age');
  
  // 实际应用场景
  Map<String, String> config = {};
  
  config['host'] ??= 'localhost';
  config['port'] ??= '8080';
  config['protocol'] ??= 'http';
  
  print('配置: $config');
  
  // 再次赋值不会改变已有值
  config['host'] ??= 'production.com';
  config['port'] ??= '443';
  
  print('再次赋值后: $config'); // 值不变
}

4. 赋值运算符的返回值

dart 复制代码
void demonstrateAssignmentReturn() {
  int a, b, c;
  
  // 赋值运算符返回被赋的值
  a = b = c = 10;
  print('a=$a, b=$b, c=$c');
  
  // 复合赋值也返回值
  int x = 5;
  int y = (x += 3); // x变为8,y也是8
  print('x=$x, y=$y');
  
  // 在条件表达式中使用赋值
  int value = 0;
  while ((value += 2) < 10) {
    print('当前值: $value');
  }
  print('最终值: $value');
  
  // 在函数调用中使用赋值
  void processValue(int val) {
    print('处理值: $val');
  }
  
  int number = 0;
  processValue(number = 42); // 赋值并传递
  print('number现在是: $number');
}

5. 列表和映射的赋值操作

dart 复制代码
void demonstrateCollectionAssignment() {
  // 列表赋值
  List<int> numbers = [1, 2, 3, 4, 5];
  print('原始列表: $numbers');
  
  // 索引赋值
  numbers[0] = 10;
  numbers[2] = 30;
  print('修改后: $numbers');
  
  // 映射赋值
  Map<String, int> scores = {'Alice': 85, 'Bob': 90};
  print('原始分数: $scores');
  
  // 键值赋值
  scores['Alice'] = 95;
  scores['Charlie'] = 88;
  print('修改后: $scores');
  
  // 使用复合赋值
  scores['Alice'] += 5;
  scores['Bob'] -= 2;
  print('复合赋值后: $scores');
  
  // 空合并赋值在集合中的使用
  scores['David'] ??= 75;
  scores['Alice'] ??= 60; // 不会改变,因为Alice已存在
  print('空合并赋值后: $scores');
  
  // 列表的复合赋值(需要自定义)
  List<int> list1 = [1, 2, 3];
  List<int> list2 = [4, 5, 6];
  
  list1.addAll(list2); // 相当于 list1 += list2 的效果
  print('合并后的列表: $list1');
}

6. 赋值运算符与对象

dart 复制代码
class Counter {
  int value;
  
  Counter(this.value);
  
  // 重载复合赋值运算符的效果需要通过方法实现
  Counter operator +(int increment) {
    return Counter(value + increment);
  }
  
  Counter operator -(int decrement) {
    return Counter(value - decrement);
  }
  
  void increment([int step = 1]) {
    value += step;
  }
  
  void decrement([int step = 1]) {
    value -= step;
  }
  
  @override
  String toString() => 'Counter($value)';
}

void demonstrateObjectAssignment() {
  Counter counter = Counter(10);
  print('初始计数器: $counter');
  
  // 对象的赋值创建新对象
  Counter newCounter = counter + 5;
  print('原计数器: $counter');
  print('新计数器: $newCounter');
  
  // 修改对象内部状态
  counter.increment(3);
  print('增加后的计数器: $counter');
  
  // 引用赋值
  Counter aliasCounter = counter;
  aliasCounter.increment(2);
  print('原计数器: $counter');        // 也会改变
  print('别名计数器: $aliasCounter'); // 指向同一对象
  
  // 深拷贝 vs 浅拷贝
  List<int> originalList = [1, 2, 3];
  List<int> shallowCopy = originalList;        // 浅拷贝(引用)
  List<int> deepCopy = List.from(originalList); // 深拷贝
  
  originalList.add(4);
  
  print('原始列表: $originalList');    // [1, 2, 3, 4]
  print('浅拷贝: $shallowCopy');       // [1, 2, 3, 4] (受影响)
  print('深拷贝: $deepCopy');          // [1, 2, 3] (不受影响)
}

类型运算符

1. is 运算符(类型检查)

dart 复制代码
void demonstrateIsOperator() {
  var value = 'Hello World';
  
  // 基本类型检查
  print('value is String: ${value is String}');     // true
  print('value is int: ${value is int}');           // false
  print('value is Object: ${value is Object}');     // true
  
  // 数字类型检查
  num number = 42;
  print('number is num: ${number is num}');         // true
  print('number is int: ${number is int}');         // true
  print('number is double: ${number is double}');   // false
  
  double decimal = 3.14;
  print('decimal is num: ${decimal is num}');       // true
  print('decimal is double: ${decimal is double}'); // true
  print('decimal is int: ${decimal is int}');       // false
  
  // 集合类型检查
  List<String> names = ['Alice', 'Bob'];
  print('names is List: ${names is List}');                    // true
  print('names is List<String>: ${names is List<String>}');    // true
  print('names is List<int>: ${names is List<int>}');          // false
  print('names is Iterable: ${names is Iterable}');            // true
  
  Map<String, int> scores = {'Alice': 95};
  print('scores is Map: ${scores is Map}');                         // true
  print('scores is Map<String, int>: ${scores is Map<String, int>}'); // true
}

2. is! 运算符(类型否定检查)

dart 复制代码
void demonstrateIsNotOperator() {
  var value = 123;
  
  // 类型否定检查
  print('value is! String: ${value is! String}');   // true
  print('value is! int: ${value is! int}');         // false
  print('value is! num: ${value is! num}');         // false
  
  // 在条件语句中使用
  if (value is! String) {
    print('value不是字符串,它是${value.runtimeType}');
  }
  
  // 与null检查结合
  String? nullableString;
  print('nullableString is! String: ${nullableString is! String}'); // true
  
  nullableString = 'Hello';
  print('nullableString is! String: ${nullableString is! String}'); // false
}

3. as 运算符(类型转换)

dart 复制代码
void demonstrateAsOperator() {
  // 安全的向下转型
  Object obj = 'Hello World';
  
  // 将Object转换为String
  String str = obj as String;
  print('转换后的字符串: $str');
  print('字符串长度: ${str.length}');
  
  // 数字转换
  num numValue = 42;
  int intValue = numValue as int;
  print('转换后的整数: $intValue');
  
  // 集合转换
  List<Object> objectList = ['a', 'b', 'c'];
  List<String> stringList = objectList as List<String>;
  print('转换后的字符串列表: $stringList');
  
  // 危险的转换(运行时错误)
  try {
    Object wrongType = 123;
    String wrongCast = wrongType as String; // 抛出TypeError
    print('这行不会执行: $wrongCast');
  } catch (e) {
    print('类型转换错误: $e');
  }
}

4. 安全的类型转换模式

dart 复制代码
// 安全转换函数
T? safeCast<T>(dynamic value) {
  return value is T ? value as T : null;
}

// 带默认值的安全转换
T safeCastWithDefault<T>(dynamic value, T defaultValue) {
  return value is T ? value as T : defaultValue;
}

void demonstrateSafeTypeCasting() {
  // 使用安全转换
  Object mixedValue = 'Hello';
  
  String? safeString = safeCast<String>(mixedValue);
  int? safeInt = safeCast<int>(mixedValue);
  
  print('安全字符串转换: $safeString');  // Hello
  print('安全整数转换: $safeInt');      // null
  
  // 使用带默认值的安全转换
  String stringResult = safeCastWithDefault<String>(mixedValue, 'Default');
  int intResult = safeCastWithDefault<int>(mixedValue, 0);
  
  print('字符串结果: $stringResult');   // Hello
  print('整数结果: $intResult');       // 0
  
  // 实际应用:处理JSON数据
  Map<String, dynamic> json = {
    'name': 'Alice',
    'age': 25,
    'score': 95.5,
    'active': true,
  };
  
  String name = safeCastWithDefault<String>(json['name'], 'Unknown');
  int age = safeCastWithDefault<int>(json['age'], 0);
  double score = safeCastWithDefault<double>(json['score'], 0.0);
  bool isActive = safeCastWithDefault<bool>(json['active'], false);
  
  print('姓名: $name, 年龄: $age, 分数: $score, 活跃: $isActive');
}

5. 类型检查在继承中的应用

dart 复制代码
abstract class Animal {
  String name;
  Animal(this.name);
  void makeSound();
}

class Dog extends Animal {
  String breed;
  
  Dog(String name, this.breed) : super(name);
  
  @override
  void makeSound() => print('$name汪汪叫');
  
  void wagTail() => print('$name摇尾巴');
}

class Cat extends Animal {
  bool isIndoor;
  
  Cat(String name, this.isIndoor) : super(name);
  
  @override
  void makeSound() => print('$name喵喵叫');
  
  void climb() => print('$name爬树');
}

class Bird extends Animal {
  double wingspan;
  
  Bird(String name, this.wingspan) : super(name);
  
  @override
  void makeSound() => print('$name啁啾叫');
  
  void fly() => print('$name飞翔');
}

void demonstrateInheritanceTypeChecking() {
  List<Animal> animals = [
    Dog('旺财', '金毛'),
    Cat('咪咪', true),
    Bird('小黄', 20.5),
    Dog('大黄', '土狗'),
  ];
  
  print('=== 类型检查和特定行为 ===');
  for (Animal animal in animals) {
    print('\n${animal.name} (${animal.runtimeType}):');
    animal.makeSound();
    
    // 类型检查和安全转换
    if (animal is Dog) {
      Dog dog = animal; // 自动类型提升
      print('品种: ${dog.breed}');
      dog.wagTail();
    } else if (animal is Cat) {
      Cat cat = animal as Cat; // 显式转换
      print('室内猫: ${cat.isIndoor}');
      cat.climb();
    } else if (animal is Bird) {
      (animal as Bird).fly(); // 内联转换
      print('翼展: ${(animal as Bird).wingspan}cm');
    }
  }
  
  print('\n=== 统计不同类型的动物 ===');
  int dogCount = animals.where((animal) => animal is Dog).length;
  int catCount = animals.where((animal) => animal is Cat).length;
  int birdCount = animals.where((animal) => animal is Bird).length;
  
  print('狗: $dogCount只, 猫: $catCount只, 鸟: $birdCount只');
  
  print('\n=== 类型过滤 ===');
  List<Dog> dogs = animals.whereType<Dog>().toList();
  List<Cat> cats = animals.whereType<Cat>().toList();
  
  print('所有狗: ${dogs.map((d) => '${d.name}(${d.breed})').join(', ')}');
  print('所有猫: ${cats.map((c) => '${c.name}(室内:${c.isIndoor})').join(', ')}');
}

6. 泛型中的类型检查

dart 复制代码
class Container<T> {
  T _value;
  
  Container(this._value);
  
  T get value => _value;
  
  set value(T newValue) {
    _value = newValue;
  }
  
  // 检查是否可以存储特定类型
  bool canStore<R>() {
    return _value is R;
  }
  
  // 安全获取特定类型的值
  R? getAs<R>() {
    return _value is R ? _value as R : null;
  }
  
  // 类型转换
  Container<R> cast<R>() {
    if (_value is R) {
      return Container<R>(_value as R);
    }
    throw TypeError();
  }
  
  @override
  String toString() => 'Container<$T>($_value)';
}

void demonstrateGenericTypeChecking() {
  // 创建不同类型的容器
  Container<Object> objectContainer = Container<Object>('Hello');
  Container<String> stringContainer = Container<String>('World');
  Container<int> intContainer = Container<int>(42);
  
  print('对象容器: $objectContainer');
  print('字符串容器: $stringContainer');
  print('整数容器: $intContainer');
  
  // 类型检查
  print('\n=== 类型检查 ===');
  print('objectContainer可以存储String: ${objectContainer.canStore<String>()}');
  print('objectContainer可以存储int: ${objectContainer.canStore<int>()}');
  print('stringContainer可以存储String: ${stringContainer.canStore<String>()}');
  print('intContainer可以存储String: ${intContainer.canStore<String>()}');
  
  // 安全获取
  print('\n=== 安全获取 ===');
  String? strFromObject = objectContainer.getAs<String>();
  int? intFromObject = objectContainer.getAs<int>();
  String? strFromString = stringContainer.getAs<String>();
  
  print('从对象容器获取字符串: $strFromObject');
  print('从对象容器获取整数: $intFromObject');
  print('从字符串容器获取字符串: $strFromString');
  
  // 类型转换
  print('\n=== 类型转换 ===');
  try {
    Container<String> convertedContainer = objectContainer.cast<String>();
    print('转换成功: $convertedContainer');
  } catch (e) {
    print('转换失败: $e');
  }
}

条件运算符

1. 三元条件运算符 (? :)

dart 复制代码
void demonstrateTernaryOperator() {
  int age = 18;
  String status = age >= 18 ? '成年人' : '未成年人';
  print('年龄$age,状态:$status');
  
  // 嵌套三元运算符
  int score = 85;
  String grade = score >= 90 ? 'A' : 
                 score >= 80 ? 'B' : 
                 score >= 70 ? 'C' : 
                 score >= 60 ? 'D' : 'F';
  print('分数$score,等级:$grade');
  
  // 在函数调用中使用
  void printMessage(bool isSuccess) {
    print(isSuccess ? '操作成功' : '操作失败');
  }
  
  printMessage(true);
  printMessage(false);
  
  // 返回不同类型(需要有公共基类)
  bool useString = true;
  Object result = useString ? 'Hello' : 42;
  print('结果: $result (${result.runtimeType})');
  
  // 在集合初始化中使用
  bool includOptional = false;
  List<String> items = [
    'item1',
    'item2',
    if (includOptional) 'optional_item', // 更好的方式
    // includOptional ? 'optional_item' : null, // 这样会包含null
  ].where((item) => item != null).cast<String>().toList();
  
  print('项目列表: $items');
}

2. 空合并运算符 (??)

dart 复制代码
void demonstrateNullCoalescingOperator() {
  String? name;
  String? email;
  
  // 基本用法:如果左侧为null,使用右侧的值
  String displayName = name ?? 'Guest';
  String contactEmail = email ?? 'no-email@example.com';
  
  print('显示名称: $displayName');
  print('联系邮箱: $contactEmail');
  
  // 链式空合并
  String? firstName;
  String? lastName;
  String? nickname;
  
  String finalName = firstName ?? lastName ?? nickname ?? 'Anonymous';
  print('最终名称: $finalName');
  
  // 与方法调用结合
  String? getUserName() => null;
  String? getDefaultName() => 'DefaultUser';
  
  String userName = getUserName() ?? getDefaultName() ?? 'Unknown';
  print('用户名: $userName');
  
  // 在集合中使用
  List<String>? optionalList;
  List<String> safeList = optionalList ?? [];
  print('安全列表: $safeList');
  
  Map<String, String>? optionalMap;
  Map<String, String> safeMap = optionalMap ?? {};
  print('安全映射: $safeMap');
  
  // 数值的空合并
  int? optionalAge;
  double? optionalHeight;
  
  int age = optionalAge ?? 0;
  double height = optionalHeight ?? 0.0;
  
  print('年龄: $age, 身高: $height');
}

3. 空合并赋值运算符 (??=)

dart 复制代码
class UserPreferences {
  String? theme;
  String? language;
  int? fontSize;
  bool? notifications;
  
  void setDefaults() {
    // 只有当值为null时才设置默认值
    theme ??= 'light';
    language ??= 'zh-CN';
    fontSize ??= 14;
    notifications ??= true;
  }
  
  @override
  String toString() {
    return 'UserPreferences(theme: $theme, language: $language, fontSize: $fontSize, notifications: $notifications)';
  }
}

void demonstrateNullCoalescingAssignment() {
  UserPreferences prefs = UserPreferences();
  print('初始偏好: $prefs');
  
  prefs.setDefaults();
  print('设置默认值后: $prefs');
  
  // 再次设置默认值不会改变已有值
  prefs.theme = 'dark';
  prefs.setDefaults();
  print('再次设置默认值后: $prefs');
  
  // 在映射中使用
  Map<String, int> cache = {};
  
  String key1 = 'user_123';
  String key2 = 'user_456';
  
  // 如果键不存在,设置默认值
  cache[key1] ??= 0;
  cache[key1] = cache[key1]! + 1; // 增加计数
  
  cache[key2] ??= 0;
  cache[key2] = cache[key2]! + 1;
  
  cache[key1] ??= 0;
  cache[key1] = cache[key1]! + 1;
  
  print('缓存计数: $cache');
  
  // 在列表中使用
  Map<String, List<String>> groups = {};
  
  void addToGroup(String groupName, String item) {
    groups[groupName] ??= [];
    groups[groupName]!.add(item);
  }
  
  addToGroup('fruits', 'apple');
  addToGroup('fruits', 'banana');
  addToGroup('vegetables', 'carrot');
  addToGroup('fruits', 'orange');
  
  print('分组: $groups');
}

4. 条件成员访问运算符 (?.)

dart 复制代码
class Address {
  String street;
  String city;
  String? zipCode;
  
  Address(this.street, this.city, [this.zipCode]);
  
  @override
  String toString() => '$street, $city ${zipCode ?? ''}';
}

class Person {
  String name;
  Address? address;
  List<String>? hobbies;
  
  Person(this.name, [this.address, this.hobbies]);
  
  String? getZipCode() => address?.zipCode;
  
  @override
  String toString() => 'Person(name: $name, address: $address)';
}

void demonstrateConditionalAccess() {
  // 创建有地址的人
  Person person1 = Person(
    'Alice',
    Address('123 Main St', 'New York', '10001'),
    ['reading', 'swimming']
  );
  
  // 创建没有地址的人
  Person person2 = Person('Bob');
  
  print('=== 条件成员访问 ===');
  
  // 安全访问嵌套属性
  print('${person1.name}的邮编: ${person1.address?.zipCode}');
  print('${person2.name}的邮编: ${person2.address?.zipCode}');
  
  // 安全方法调用
  print('${person1.name}的城市长度: ${person1.address?.city.length}');
  print('${person2.name}的城市长度: ${person2.address?.city.length}');
  
  // 链式安全访问
  print('${person1.name}的街道首字母: ${person1.address?.street[0]}');
  print('${person2.name}的街道首字母: ${person2.address?.street[0]}');
  
  // 安全访问集合
  print('${person1.name}的爱好数量: ${person1.hobbies?.length}');
  print('${person2.name}的爱好数量: ${person2.hobbies?.length}');
  
  print('${person1.name}的第一个爱好: ${person1.hobbies?[0]}');
  print('${person2.name}的第一个爱好: ${person2.hobbies?[0]}');
  
  // 结合空合并运算符
  String person1City = person1.address?.city ?? 'Unknown';
  String person2City = person2.address?.city ?? 'Unknown';
  
  print('${person1.name}的城市: $person1City');
  print('${person2.name}的城市: $person2City');
}

5. 条件运算符的组合使用

dart 复制代码
class ApiResponse<T> {
  final bool success;
  final T? data;
  final String? error;
  final int? statusCode;
  
  ApiResponse({
    required this.success,
    this.data,
    this.error,
    this.statusCode,
  });
  
  @override
  String toString() => 'ApiResponse(success: $success, data: $data, error: $error, statusCode: $statusCode)';
}

class User {
  final int id;
  final String name;
  final String email;
  final bool isActive;
  
  User({required this.id, required this.name, required this.email, this.isActive = true});
  
  @override
  String toString() => 'User(id: $id, name: $name, email: $email, active: $isActive)';
}

void demonstrateComplexConditionalOperators() {
  // 模拟API响应
  ApiResponse<User>? successResponse = ApiResponse(
    success: true,
    data: User(id: 1, name: 'Alice', email: 'alice@example.com'),
    statusCode: 200,
  );
  
  ApiResponse<User>? errorResponse = ApiResponse(
    success: false,
    error: 'User not found',
    statusCode: 404,
  );
  
  ApiResponse<User>? nullResponse;
  
  print('=== 复杂条件运算符组合 ===');
  
  // 安全获取用户信息
  String getUserInfo(ApiResponse<User>? response) {
    return response?.success == true
        ? 'User: ${response?.data?.name ?? 'Unknown'} (${response?.data?.email ?? 'No email'})'
        : 'Error: ${response?.error ?? 'Unknown error'}';
  }
  
  print('成功响应: ${getUserInfo(successResponse)}');
  print('错误响应: ${getUserInfo(errorResponse)}');
  print('空响应: ${getUserInfo(nullResponse)}');
  
  // 复杂的条件逻辑
  String getStatusMessage(ApiResponse<User>? response) {
    // 多层条件检查
    return response == null
        ? 'No response'
        : !response.success
            ? 'Request failed: ${response.error ?? 'Unknown error'}'
            : response.data == null
                ? 'No user data'
                : response.data!.isActive
                    ? 'Active user: ${response.data!.name}'
                    : 'Inactive user: ${response.data!.name}';
  }
  
  print('\n=== 状态消息 ===');
  print('成功响应状态: ${getStatusMessage(successResponse)}');
  print('错误响应状态: ${getStatusMessage(errorResponse)}');
  print('空响应状态: ${getStatusMessage(nullResponse)}');
  
  // 使用条件运算符进行数据转换
  Map<String, dynamic> responseToJson(ApiResponse<User>? response) {
    return {
      'status': response?.success ?? false ? 'success' : 'error',
      'message': response?.success ?? false
          ? 'Request completed successfully'
          : response?.error ?? 'Unknown error occurred',
      'user': response?.data != null
          ? {
              'id': response!.data!.id,
              'name': response.data!.name,
              'email': response.data!.email,
              'active': response.data!.isActive,
            }
          : null,
      'statusCode': response?.statusCode ?? 500,
    };
  }
  
  print('\n=== JSON转换 ===');
  print('成功响应JSON: ${responseToJson(successResponse)}');
  print('错误响应JSON: ${responseToJson(errorResponse)}');
  print('空响应JSON: ${responseToJson(nullResponse)}');
}

6. 条件运算符的性能考虑

dart 复制代码
class ExpensiveOperation {
  static int callCount = 0;
  
  static String performOperation(String input) {
    callCount++;
    print('执行昂贵操作 #$callCount: $input');
    // 模拟耗时操作
    return input.toUpperCase();
  }
  
  static String? performNullableOperation(String input) {
    callCount++;
    print('执行可空操作 #$callCount: $input');
    return input.isEmpty ? null : input.toLowerCase();
  }
}

void demonstrateConditionalPerformance() {
  print('=== 条件运算符性能考虑 ===');
  
  // 短路求值的好处
  String? input1 = null;
  String? input2 = 'Hello';
  
  ExpensiveOperation.callCount = 0;
  
  // 使用 ?? 运算符(短路求值)
  String result1 = input1 ?? ExpensiveOperation.performOperation('default1');
  String result2 = input2 ?? ExpensiveOperation.performOperation('default2');
  
  print('结果1: $result1');
  print('结果2: $result2');
  print('总调用次数: ${ExpensiveOperation.callCount}'); // 只调用1次
  
  print('\n--- 对比:总是计算两边 ---');
  ExpensiveOperation.callCount = 0;
  
  // 如果不使用短路求值(错误示例)
  String getValue(String? input, String defaultValue) {
    String def = ExpensiveOperation.performOperation(defaultValue);
    return input ?? def; // 总是计算默认值
  }
  
  String result3 = getValue(null, 'default3');
  String result4 = getValue('World', 'default4');
  
  print('结果3: $result3');
  print('结果4: $result4');
  print('总调用次数: ${ExpensiveOperation.callCount}'); // 调用2次
  
  // 缓存计算结果
  print('\n--- 使用缓存优化 ---');
  Map<String, String> cache = {};
  
  String getCachedValue(String? input, String key) {
    return input ?? (cache[key] ??= ExpensiveOperation.performOperation(key));
  }
  
  ExpensiveOperation.callCount = 0;
  
  String cached1 = getCachedValue(null, 'cached_key');
  String cached2 = getCachedValue(null, 'cached_key'); // 使用缓存
  String cached3 = getCachedValue('Direct', 'cached_key'); // 不使用缓存
  
  print('缓存结果1: $cached1');
  print('缓存结果2: $cached2');
  print('缓存结果3: $cached3');
  print('总调用次数: ${ExpensiveOperation.callCount}'); // 只调用1次
  print('缓存内容: $cache');
}

级联运算符

1. 基本级联运算符 (..)

dart 复制代码
class Person {
  String? name;
  int? age;
  String? email;
  List<String> hobbies = [];
  
  void setName(String name) => this.name = name;
  void setAge(int age) => this.age = age;
  void setEmail(String email) => this.email = email;
  void addHobby(String hobby) => hobbies.add(hobby);
  
  @override
  String toString() => 'Person(name: $name, age: $age, email: $email, hobbies: $hobbies)';
}

void demonstrateBasicCascade() {
  // 不使用级联运算符的传统方式
  Person person1 = Person();
  person1.setName('Alice');
  person1.setAge(25);
  person1.setEmail('alice@example.com');
  person1.addHobby('reading');
  person1.addHobby('swimming');
  
  print('传统方式: $person1');
  
  // 使用级联运算符
  Person person2 = Person()
    ..setName('Bob')
    ..setAge(30)
    ..setEmail('bob@example.com')
    ..addHobby('gaming')
    ..addHobby('cooking');
  
  print('级联方式: $person2');
  
  // 级联运算符与属性访问
  Person person3 = Person()
    ..name = 'Charlie'
    ..age = 28
    ..email = 'charlie@example.com'
    ..hobbies.add('music')
    ..hobbies.add('travel');
  
  print('属性级联: $person3');
}

2. 空安全级联运算符 (?..)

dart 复制代码
void demonstrateNullAwareCascade() {
  List<int>? nullableList = [1, 2, 3];
  List<int>? emptyList = null;
  
  // 使用空安全级联运算符
  nullableList
    ?..add(4)
    ..add(5)
    ..sort();
  
  print('nullableList: $nullableList');
  
  // 对null对象使用空安全级联
  emptyList
    ?..add(1)    // 这些操作都不会执行
    ..add(2)
    ..sort();
  
  print('emptyList: $emptyList'); // 仍然是null
  
  // 级联运算符与集合
  List<String> names = []
    ..add('Alice')
    ..add('Bob')
    ..add('Charlie')
    ..sort()
    ..shuffle();
  
  print('names: $names');
}

其他运算符

1. 函数调用运算符 ()

dart 复制代码
class Calculator {
  double Function(double, double) operation;
  
  Calculator(this.operation);
  
  // 实现call方法,使对象可调用
  double call(double a, double b) => operation(a, b);
}

void demonstrateCallOperator() {
  // 创建可调用对象
  Calculator adder = Calculator((a, b) => a + b);
  Calculator multiplier = Calculator((a, b) => a * b);
  
  // 使用函数调用运算符
  print('5 + 3 = ${adder(5, 3)}');        // 使用call方法
  print('4 * 6 = ${multiplier(4, 6)}');   // 使用call方法
  
  // 函数作为第一类对象
  List<int Function(int)> functions = [
    (x) => x * 2,
    (x) => x + 1,
    (x) => x * x,
  ];
  
  int value = 5;
  for (var func in functions) {
    value = func(value);
    print('当前值: $value');
  }
}

2. 索引运算符 []

dart 复制代码
class Matrix {
  List<List<int>> _data;
  
  Matrix(this._data);
  
  // 实现索引运算符
  List<int> operator [](int row) => _data[row];
  
  // 实现索引赋值运算符
  void operator []=(int row, List<int> value) {
    _data[row] = value;
  }
  
  // 自定义二维索引
  int getValue(int row, int col) => _data[row][col];
  
  void setValue(int row, int col, int value) {
    _data[row][col] = value;
  }
  
  @override
  String toString() => _data.toString();
}

void demonstrateIndexOperator() {
  Matrix matrix = Matrix([
    [1, 2, 3],
    [4, 5, 6],
    [7, 8, 9]
  ]);
  
  print('原始矩阵: $matrix');
  
  // 使用索引运算符访问
  print('第一行: ${matrix[0]}');
  print('第二行第三列: ${matrix[1][2]}');
  
  // 使用索引运算符修改
  matrix[0] = [10, 20, 30];
  matrix[1][1] = 50;
  
  print('修改后矩阵: $matrix');
  
  // Map的索引运算符
  Map<String, int> scores = {'Alice': 95, 'Bob': 87};
  print('Alice的分数: ${scores['Alice']}');
  
  scores['Charlie'] = 92;
  print('添加Charlie后: $scores');
}

3. 成员访问运算符 (.)

dart 复制代码
class Address {
  String street;
  String city;
  
  Address(this.street, this.city);
  
  @override
  String toString() => '$street, $city';
}

class Person {
  String name;
  Address address;
  
  Person(this.name, this.address);
  
  String getFullAddress() => '${address.street}, ${address.city}';
}

void demonstrateMemberAccess() {
  Person person = Person('Alice', Address('123 Main St', 'New York'));
  
  // 成员访问运算符
  print('姓名: ${person.name}');
  print('街道: ${person.address.street}');
  print('城市: ${person.address.city}');
  print('完整地址: ${person.getFullAddress()}');
  
  // 链式成员访问
  String cityName = person.address.city.toUpperCase();
  print('大写城市名: $cityName');
}

运算符重载

1. 算术运算符重载

dart 复制代码
class Vector2D {
  final double x, y;
  
  const Vector2D(this.x, this.y);
  
  // 加法运算符重载
  Vector2D operator +(Vector2D other) {
    return Vector2D(x + other.x, y + other.y);
  }
  
  // 减法运算符重载
  Vector2D operator -(Vector2D other) {
    return Vector2D(x - other.x, y - other.y);
  }
  
  // 乘法运算符重载(标量乘法)
  Vector2D operator *(double scalar) {
    return Vector2D(x * scalar, y * scalar);
  }
  
  // 除法运算符重载
  Vector2D operator /(double scalar) {
    if (scalar == 0) throw ArgumentError('除数不能为0');
    return Vector2D(x / scalar, y / scalar);
  }
  
  // 一元负号运算符重载
  Vector2D operator -() {
    return Vector2D(-x, -y);
  }
  
  // 相等运算符重载
  @override
  bool operator ==(Object other) =>
      identical(this, other) ||
      other is Vector2D && x == other.x && y == other.y;
  
  @override
  int get hashCode => Object.hash(x, y);
  
  // 索引运算符重载
  double operator [](int index) {
    switch (index) {
      case 0: return x;
      case 1: return y;
      default: throw RangeError('索引必须是0或1');
    }
  }
  
  // 计算向量的模长
  double get magnitude => math.sqrt(x * x + y * y);
  
  @override
  String toString() => 'Vector2D($x, $y)';
}

void demonstrateOperatorOverloading() {
  Vector2D v1 = Vector2D(3, 4);
  Vector2D v2 = Vector2D(1, 2);
  
  print('v1: $v1');
  print('v2: $v2');
  print('v1的模长: ${v1.magnitude}');
  
  // 使用重载的运算符
  Vector2D sum = v1 + v2;
  Vector2D diff = v1 - v2;
  Vector2D scaled = v1 * 2;
  Vector2D divided = v1 / 2;
  Vector2D negated = -v1;
  
  print('v1 + v2 = $sum');
  print('v1 - v2 = $diff');
  print('v1 * 2 = $scaled');
  print('v1 / 2 = $divided');
  print('-v1 = $negated');
  
  // 使用索引运算符
  print('v1[0] = ${v1[0]}, v1[1] = ${v1[1]}');
  
  // 相等性比较
  Vector2D v3 = Vector2D(3, 4);
  print('v1 == v3: ${v1 == v3}');
  print('v1 == v2: ${v1 == v2}');
}

2. 比较运算符重载

dart 复制代码
class Student implements Comparable<Student> {
  final String name;
  final int score;
  final int age;
  
  Student(this.name, this.score, this.age);
  
  @override
  int compareTo(Student other) {
    // 首先按分数降序排列
    int scoreComparison = other.score.compareTo(score);
    if (scoreComparison != 0) return scoreComparison;
    
    // 分数相同则按年龄升序排列
    int ageComparison = age.compareTo(other.age);
    if (ageComparison != 0) return ageComparison;
    
    // 年龄也相同则按姓名字母序排列
    return name.compareTo(other.name);
  }
  
  // 重载比较运算符
  bool operator <(Student other) => compareTo(other) < 0;
  bool operator <=(Student other) => compareTo(other) <= 0;
  bool operator >(Student other) => compareTo(other) > 0;
  bool operator >=(Student other) => compareTo(other) >= 0;
  
  @override
  bool operator ==(Object other) =>
      identical(this, other) ||
      other is Student &&
      name == other.name &&
      score == other.score &&
      age == other.age;
  
  @override
  int get hashCode => Object.hash(name, score, age);
  
  @override
  String toString() => 'Student(name: $name, score: $score, age: $age)';
}

void demonstrateComparisonOverloading() {
  List<Student> students = [
    Student('Alice', 95, 20),
    Student('Bob', 87, 22),
    Student('Charlie', 95, 19),
    Student('David', 87, 21),
    Student('Eve', 95, 19),
  ];
  
  print('原始学生列表:');
  students.forEach(print);
  
  // 使用重载的比较运算符排序
  students.sort();
  
  print('\n排序后的学生列表:');
  students.forEach(print);
  
  // 使用重载的比较运算符
  Student alice = students.first;
  Student bob = students[3];
  
  print('\n比较运算符测试:');
  print('$alice > $bob: ${alice > bob}');
  print('$alice <= $bob: ${alice <= bob}');
}

运算符优先级和结合性

优先级表格(从高到低)

dart 复制代码
void demonstrateOperatorPrecedence() {
  // 优先级演示
  int result1 = 2 + 3 * 4;        // 14, 不是 20
  int result2 = (2 + 3) * 4;      // 20
  
  print('2 + 3 * 4 = $result1');
  print('(2 + 3) * 4 = $result2');
  
  // 逻辑运算符优先级
  bool result3 = true || false && false;   // true, 不是 false
  bool result4 = (true || false) && false; // false
  
  print('true || false && false = $result3');
  print('(true || false) && false = $result4');
  
  // 位运算符优先级
  int result5 = 5 | 3 & 1;        // 5 (先计算 3 & 1 = 1, 然后 5 | 1 = 5)
  int result6 = (5 | 3) & 1;      // 0 (先计算 5 | 3 = 7, 然后 7 & 1 = 1)
  
  print('5 | 3 & 1 = $result5');
  print('(5 | 3) & 1 = $result6');
  
  // 赋值运算符优先级最低
  int a = 1;
  int b = 2;
  int c = a = b + 1;  // 等价于 c = (a = (b + 1))
  
  print('a = $a, b = $b, c = $c');
}

完整优先级表

优先级 运算符 描述 结合性
16 () [] . ?. 后缀 左到右
15 -expr !expr ~expr ++expr --expr await expr 一元前缀
14 expr++ expr-- 一元后缀
13 * / % ~/ 乘法 左到右
12 + - 加法 左到右
11 << >> >>> 位移 左到右
10 & 按位与 左到右
9 ^ 按位异或 左到右
8 ` ` 按位或
7 >= > <= < as is is! 关系和类型测试 左到右
6 == != 相等 左到右
5 && 逻辑与 左到右
4 ` `
3 ?? 空合并 左到右
2 ? : 条件 右到左
1 .. ?.. 级联 左到右
0 = *= /= += -= &= ` = ^=` `~/=` `%=` `<<=` `>>=` `>>>=` `??=` 赋值

实际应用示例

1. 数据验证和处理

dart 复制代码
class DataProcessor {
  // 使用运算符重载创建流畅的API
  static bool Function(dynamic) operator +(bool Function(dynamic) f1, bool Function(dynamic) f2) {
    return (value) => f1(value) && f2(value);
  }
  
  static bool isNotNull(dynamic value) => value != null;
  static bool isNotEmpty(dynamic value) => value is String ? value.isNotEmpty : true;
  static bool isEmail(dynamic value) => value is String ? 
      RegExp(r'^[\w-\.]+@([\w-]+\.)+[\w-]{2,4}$').hasMatch(value) : false;
  static bool isMinLength(int min) => (dynamic value) => 
      value is String ? value.length >= min : true;
  
  static void processData(Map<String, dynamic> data) {
    // 使用条件运算符和逻辑运算符进行验证
    String name = data['name'] ?? '';
    String email = data['email'] ?? '';
    int age = data['age'] ?? 0;
    
    // 复合验证
    bool isValidName = name.isNotEmpty && name.length >= 2;
    bool isValidEmail = email.isNotEmpty && isEmail(email);
    bool isValidAge = age > 0 && age < 150;
    
    print('数据验证结果:');
    print('  姓名有效: $isValidName (值: "$name")');
    print('  邮箱有效: $isValidEmail (值: "$email")');
    print('  年龄有效: $isValidAge (值: $age)');
    
    // 使用级联运算符处理有效数据
    if (isValidName && isValidEmail && isValidAge) {
      Map<String, dynamic> processedData = {}
        ..['name'] = name.trim().toLowerCase()
        ..['email'] = email.trim().toLowerCase()
        ..['age'] = age
        ..['processed_at'] = DateTime.now().toIso8601String()
        ..['status'] = 'valid';
      
      print('处理后的数据: $processedData');
    }
  }
}

2. 构建器模式的高级应用

dart 复制代码
class QueryBuilder {
  String _table = '';
  List<String> _columns = [];
  List<String> _conditions = [];
  List<String> _orderBy = [];
  int? _limit;
  
  QueryBuilder from(String table) {
    _table = table;
    return this;
  }
  
  QueryBuilder select(List<String> columns) {
    _columns = columns;
    return this;
  }
  
  QueryBuilder where(String condition) {
    _conditions.add(condition);
    return this;
  }
  
  QueryBuilder orderBy(String column, [String direction = 'ASC']) {
    _orderBy.add('$column $direction');
    return this;
  }
  
  QueryBuilder limit(int count) {
    _limit = count;
    return this;
  }
  
  String build() {
    StringBuffer query = StringBuffer();
    
    // SELECT子句
    query.write('SELECT ');
    query.write(_columns.isEmpty ? '*' : _columns.join(', '));
    
    // FROM子句
    query.write(' FROM $_table');
    
    // WHERE子句
    if (_conditions.isNotEmpty) {
      query.write(' WHERE ${_conditions.join(' AND ')}');
    }
    
    // ORDER BY子句
    if (_orderBy.isNotEmpty) {
      query.write(' ORDER BY ${_orderBy.join(', ')}');
    }
    
    // LIMIT子句
    if (_limit != null) {
      query.write(' LIMIT $_limit');
    }
    
    return query.toString();
  }
}

void demonstrateQueryBuilder() {
  // 使用级联运算符构建复杂查询
  String query1 = QueryBuilder()
    ..from('users')
    ..select(['name', 'email', 'age'])
    ..where('age >= 18')
    ..where('status = "active"')
    ..orderBy('name')
    ..limit(10);
  
  print('查询1: ${query1.build()}');
  
  String query2 = QueryBuilder()
    ..from('products')
    ..where('price > 100')
    ..where('category = "electronics"')
    ..orderBy('price', 'DESC')
    ..limit(5);
  
  print('查询2: ${query2.build()}');
}

性能考虑

1. 运算符重载的性能影响

dart 复制代码
class PerformanceTest {
  static void compareOperatorPerformance() {
    const int iterations = 1000000;
    
    // 测试基本运算符
    Stopwatch sw1 = Stopwatch()..start();
    for (int i = 0; i < iterations; i++) {
      int result = i + i * 2 - i ~/ 2;
    }
    sw1.stop();
    print('基本运算符时间: ${sw1.elapsedMilliseconds}ms');
    
    // 测试重载运算符
    Vector2D v1 = Vector2D(1, 2);
    Vector2D v2 = Vector2D(3, 4);
    
    Stopwatch sw2 = Stopwatch()..start();
    for (int i = 0; i < iterations; i++) {
      Vector2D result = v1 + v2 - v1 * 0.5;
    }
    sw2.stop();
    print('重载运算符时间: ${sw2.elapsedMilliseconds}ms');
    
    // 测试方法调用
    Stopwatch sw3 = Stopwatch()..start();
    for (int i = 0; i < iterations; i++) {
      Vector2D temp = v1.add(v2);
      Vector2D result = temp.subtract(v1.multiply(0.5));
    }
    sw3.stop();
    print('方法调用时间: ${sw3.elapsedMilliseconds}ms');
  }
}

extension Vector2DMethods on Vector2D {
  Vector2D add(Vector2D other) => Vector2D(x + other.x, y + other.y);
  Vector2D subtract(Vector2D other) => Vector2D(x - other.x, y - other.y);
  Vector2D multiply(double scalar) => Vector2D(x * scalar, y * scalar);
}

常见陷阱和错误

1. 运算符优先级陷阱

dart 复制代码
void demonstrateCommonPitfalls() {
  // 陷阱1: 逻辑运算符优先级
  bool a = true;
  bool b = false;
  bool c = true;
  
  // 错误理解:(a || b) && c
  // 实际执行:a || (b && c)
  bool result1 = a || b && c;
  print('a || b && c = $result1'); // true
  
  // 正确的写法
  bool result2 = (a || b) && c;
  print('(a || b) && c = $result2'); // true
  
  // 陷阱2: 位运算符优先级
  int x = 5;  // 101
  int y = 3;  // 011
  
  // 错误理解:(x & y) == 1
  // 实际执行:x & (y == 1)
  bool result3 = x & y == 1;  // 编译错误!
  
  // 正确的写法
  bool result4 = (x & y) == 1;
  print('(x & y) == 1 = $result4'); // true
  
  // 陷阱3: 空合并运算符的优先级
  String? name = null;
  String? backup = 'default';
  
  // 可能的误解
  String result5 = name ?? backup.toUpperCase(); // 正确:name ?? (backup.toUpperCase())
  print('name ?? backup.toUpperCase() = $result5'); // DEFAULT
  
  // 陷阱4: 级联运算符的返回值
  List<int> list = [3, 1, 4]..sort(); // 返回List<int>
  print('排序后的列表: $list'); // [1, 3, 4]
  
  // 错误用法
  // int length = [1, 2, 3]..add(4).length; // 错误!级联返回原对象
  
  // 正确用法
  List<int> tempList = [1, 2, 3]..add(4);
  int length = tempList.length;
  print('列表长度: $length'); // 4
}

最佳实践

1. 运算符重载最佳实践

dart 复制代码
class Money {
  final int cents; // 使用分为单位避免浮点数精度问题
  final String currency;
  
  const Money(this.cents, this.currency);
  
  // 工厂构造函数
  factory Money.fromDollars(double dollars, String currency) {
    return Money((dollars * 100).round(), currency);
  }
  
  // 只重载有意义的运算符
  Money operator +(Money other) {
    if (currency != other.currency) {
      throw ArgumentError('不能加不同货币: $currency + ${other.currency}');
    }
    return Money(cents + other.cents, currency);
  }
  
  Money operator -(Money other) {
    if (currency != other.currency) {
      throw ArgumentError('不能减不同货币: $currency - ${other.currency}');
    }
    return Money(cents - other.cents, currency);
  }
  
  Money operator *(double multiplier) {
    return Money((cents * multiplier).round(), currency);
  }
  
  Money operator /(double divisor) {
    if (divisor == 0) throw ArgumentError('除数不能为0');
    return Money((cents / divisor).round(), currency);
  }
  
  // 比较运算符
  @override
  bool operator ==(Object other) =>
      identical(this, other) ||
      other is Money && cents == other.cents && currency == other.currency;
  
  @override
  int get hashCode => Object.hash(cents, currency);
  
  bool operator <(Money other) {
    if (currency != other.currency) {
      throw ArgumentError('不能比较不同货币');
    }
    return cents < other.cents;
  }
  
  bool operator >(Money other) {
    if (currency != other.currency) {
      throw ArgumentError('不能比较不同货币');
    }
    return cents > other.cents;
  }
  
  double get dollars => cents / 100.0;
  
  @override
  String toString() => '${dollars.toStringAsFixed(2)} $currency';
}

void demonstrateBestPractices() {
  Money price1 = Money.fromDollars(19.99, 'USD');
  Money price2 = Money.fromDollars(5.50, 'USD');
  
  // 运算符重载使代码更直观
  Money total = price1 + price2;
  Money discounted = total * 0.9;
  
  print('价格1: $price1');
  print('价格2: $price2');
  print('总计: $total');
  print('打折后: $discounted');
  
  // 比较运算符
  if (price1 > price2) {
    print('$price1 比 $price2 贵');
  }
}

2. 条件运算符最佳实践

dart 复制代码
class UserService {
  // 使用空合并运算符提供默认值
  static String getDisplayName(String? firstName, String? lastName, String? username) {
    return '${firstName ?? ''} ${lastName ?? ''}'.trim().ifEmpty(() => username ?? 'Guest');
  }
  
  // 使用条件运算符简化逻辑
  static String getUserStatus(bool isActive, DateTime? lastLogin) {
    return !isActive 
        ? 'Inactive'
        : lastLogin == null 
            ? 'Never logged in'
            : DateTime.now().difference(lastLogin).inDays > 30
                ? 'Inactive (30+ days)'
                : 'Active';
  }
  
  // 使用级联运算符初始化对象
  static Map<String, dynamic> createUserProfile({
    required String name,
    required String email,
    String? avatar,
    List<String>? interests,
  }) {
    return <String, dynamic>{}
      ..['name'] = name
      ..['email'] = email
      ..['avatar'] = avatar ?? 'default-avatar.png'
      ..['interests'] = interests ?? []
      ..['created_at'] = DateTime.now().toIso8601String()
      ..['status'] = 'active';
  }
}

extension StringExtensions on String {
  String ifEmpty(String Function() defaultValue) {
    return isEmpty ? defaultValue() : this;
  }
}

总结

Dart的运算符系统提供了强大而灵活的表达能力,通过掌握以下关键概念:

  1. 丰富的运算符类型:算术、比较、逻辑、位、赋值、类型、条件等
  2. 运算符重载:为自定义类型定义直观的运算符行为
  3. 空安全运算符:安全处理可空值的强大工具
  4. 级联运算符:简化对象配置和链式调用
  5. 优先级和结合性:正确理解运算符的执行顺序
  6. 性能考虑:合理使用运算符避免性能问题

结合最佳实践和常见陷阱的避免,可以编写出更加简洁、可读和高效的Dart代码。记住要根据具体场景选择合适的运算符,并始终考虑代码的可读性和维护性。


本文档基于Dart 3.x版本整理,涵盖了运算符系统的核心概念和实际应用场景。

相关推荐
农夫三拳_有点甜6 小时前
Dart Timer 全面总结指南
dart
农夫三拳_有点甜6 小时前
Dart Class API 详细总结
dart
cowice4 天前
Dart基础知识
flutter·dart
AhhhhDong11 天前
记录工作中遇到的几个Dart语言的坑和bug
dart
叽哥16 天前
Flutter面试:Dart基础2
flutter·面试·dart
fouryears_2341720 天前
Flutter InheritedWidget 详解:从生命周期到数据流动的完整解析
开发语言·flutter·客户端·dart
华科云商xiao徐25 天前
异步并发×编译性能:Dart爬虫的实战突围
爬虫·数据可视化·dart
dragon72525 天前
dart以同步方式调用异步函数引发的时序bug
dart
叽哥1 个月前
dart学习第 24 节:核心特性实战 —— 天气 API 数据解析
flutter·dart