什么是 ?? Dart 中的双问号?

Posted

技术标签:

【中文标题】什么是 ?? Dart 中的双问号?【英文标题】:What are the ?? double question marks in Dart? 【发布时间】:2019-05-30 14:30:08 【问题描述】:

以下代码行有两个问号:

final myStringList = prefs.getStringList('my_string_list_key') ?? [];

什么意思?

【问题讨论】:

【参考方案1】:

?? 双问号运算符表示“如果为空”。以下面的表达式为例。

String a = b ?? 'hello';

这意味着a 等于b,但如果b 为空,则a 等于'hello'

另一个相关的运算符是??=。例如:

b ??= 'hello';

这意味着如果b 为空,则将其设置为等于hello。否则,请勿更改。

参考

A Tour of the Dart Language: Operators Null-aware operators in Dart

条款

Dart 1.12 release news 将以下统称为 null-aware 运算符

?? -- 如果为空运算符 ??= -- null-aware assignment x?.p -- 空感知访问 x?.m() -- 可识别 null 的方法调用

【讨论】:

有趣的是为什么?而不是?在 php 中的意思完全相反。 @Vedmant 可能是因为 ? 已被三元运算符使用:String a = b == true ? 'x' : 'y';。 if-null 运算符原来只是像String a = a == null ? 'hello : a; 这样的三元空检查的简写。 @BrunoFinger ? 在 PHP 中用于三元运算符的方式相同,并且有类似 $a = $b === true ? $b : 'y' 的快捷方式,您可以键入 $a = $b === true ?: 'y' 或代替 $a = $b === true ? 'x' : $b - $a = $b === true ?? 'x' 【参考方案2】:

Dart 提供了一些方便的运算符来处理可能为 null 的值。一种是 ??= 赋值运算符,仅当变量当前为 null 时才为变量赋值:

int a; // The initial value of a is null.
a ??= 3;
print(a); // <-- Prints 3.

a ??= 5;
print(a); // <-- Still prints 3.

另一个null-aware 运算符是??,它返回左边的表达式,除非该表达式的值为null,在这种情况下,它计算并返回右边的表达式:

print(1 ?? 3); // <-- Prints 1.
print(null ?? 12); // <-- Prints 12.

【讨论】:

【参考方案3】:

这在 flutter 中经常用于覆盖的 copyWith 方法中特别有用。 下面是一个例子:

import './color.dart';
import './colors.dart';

class CoreState 
  final int counter;
  final Color backgroundColor;

  const CoreState(
    this.counter = 0,
    this.backgroundColor = Colors.white,
  );

  CoreState copyWith(
    int? counter,
    Color? backgroundColor,
  ) =>
      CoreState(
        counter: counter ?? this.counter,
        backgroundColor: backgroundColor ?? this.backgroundColor,
      );

  @override
  bool operator ==(Object other) =>
      identical(this, other) ||
          other is CoreState &&
              runtimeType == other.runtimeType &&
              counter == other.counter &&
              backgroundColor == other.backgroundColor;

  @override
  int get hashCode => counter.hashCode ^ backgroundColor.hashCode;


  @override
  String toString() 
    return "counter: $counter\n"
            "color:$backgroundColor";
  

【讨论】:

我们在这里做的是给用户机会覆盖,注意copywith方法中可以为空的参数,然后检查参数是否为空,默认返回定义的现有值

以上是关于什么是 ?? Dart 中的双问号?的主要内容,如果未能解决你的问题,请参考以下文章

如何在小数点后将 Dart 中的双精度数舍入到给定的精度?

Java的方法参数中的双感叹号和#号是啥意思?

c#中的?是什么意思

c语言的双冒号是啥意思::

在 FLUTTER/DART 中,为啥我们有时在声明变量的时候会在“String”后面加上问号?

什么是美元? (美元问号)shell 脚本中的变量? [复制]