Check how many of these codes exist in your Flutter project

if(xxx ! =null && xxx.isNotEmpty)
Copy the code

I have to say, I really don’t like the idea of thinking about the condition and then thinking about the “if” in reverse order of code (after all, everyone lives in the world of “TENET” 😏), especially if the condition is long.

To eliminate== null

Dart is known to have? And?? This nulls operator, so the above code can be simplified as follows:

String a = "dart";
if(a? .isNotEmpty ??false) {
   print('😏');
}
Copy the code

But it’s still a hassle

Try wrapping an extension function

Add the isNullOrEmpty extension function to commonly used types

extension MapExtension on Map {
  bool get isNullOrEmpty => (this= =null || this.isEmpty);
}

extension IterableExtension on 可迭代 {
  bool get isNullOrEmpty => (this= =null || this.isEmpty);
}

extension StringExtension on String {
  bool get isNullOrEmpty => (this= =null || this.isEmpty);
}
Copy the code

Ok, now we can write:

String a = null;
if(! a.isNullOrEmpty) {print("πŸ˜’");
} else print("Shit");
Copy the code

However, there is another scenario that does not deal with null branches and only deals with Empty or notEmpty

Let’s take Kotlin’s scheme and add an extension function to bool

Write first

String a = ""; a? .isEmpty? .yes(() {print("Yes!"); })? .orElse(() {print("No! God No!");
})
Copy the code

If you still want to determine the empty branch, you can add??

It doesn’t look as beautiful as Kotlin, but at least you don’t have to write if, and the code is implemented at πŸ‘‡

class BooleanExt<T extends Object> {
  T orElse(T block()) {
    if (this is OrElse) {
      return block() ?? Null;
    } else {
      return (this as WithData).data ?? Null; }}}class OrElse extends BooleanExt<Object> {}

class WithData<T> extends BooleanExt<T> {
  final T data;

  WithData(this.data);
}

extension BoolExtension<T> on bool {
  BooleanExt yes(T block()) {
    if (this) {
      return WithData(block());
    } else {
      return OrElse();
    }
  }

  BooleanExt no(T block()) {
    if (this) {
      return OrElse();
    } else {
      returnWithData(block()); }}}Copy the code

The above code is based on the current stable version of the syntax, but some time ago Dart released an experimental feature that added a full version of null safety

New Dart “Air Safety”

Nullsafety.dartpad. Cn/nullsafety.dartpad/nullsafety.dartpad/nullsafety.dartpad/nullsafety.dartpad / With the new null security, the isNullorEmpty implementation and call above should look like this:

extension IterableExtension on Iterable? {
  bool get isNullOrEmpty => (this= =null || this! .isEmpty); }///
List<String>? a = null;
if (a.isNullOrEmpty) {
  print("DOG");
} else {
  print("Cat");
}
Copy the code

Emmm, can be found that the language is not too smart, I wrote this clearly in front of all the = = null | |, call back or to add! Operator force not null, in Kotlin, here you can judge intelligently, Kotlin really sweet 🌝.

conclusion

Dart started out humble, but it’s progressing. With extension functions and strict empty safety, the next step is to consider supporting DSL syntax 😏