🚵

Dart3.0を追う

2023/06/19に公開

海外の動画見て勉強してキャッチアップしてみた

こちらの動画で新しく出たレコードやパターンなるものを学習できます。

https://www.youtube.com/watch?v=dBwvc-U8q-c

タプルについて学ぶ

List型のメソッドにデータ型が2個あるとdynamicにしないとエラーが出てしまいます。

List<dynamic> givemeSomeDoubles() {
  return [4.5, 'Hey'];
}

この問題を解決するために、タプルという新機能を使います。今回は複数のデータ型を扱うメソッドを作ってみましょう。List<dynamic>を消して、()を書いて使うデータ型を定義することで、値を$をつけて参照することができます。これは、他の言語でもあるのですが、タプルと呼ばれているものです。

void main() {
  final values = givemeSomeDoubles();
  print(values.$1);// $1は、タプルの1番目の要素を取り出す
  print(values.$2);// $2は、タプルの2番目の要素を取り出す
}

// (double, String)は、タプルというもので、複数の値を返すことができる
(double, String) givemeSomeDoubles() {
  return (4.5, 'Hey');
}

実行結果

4.5
Hey

タプルには、JavaScriptの分割代入みたいな機能もあります。

void main() {
  // このように、タプルの要素を、それぞれの変数に代入することができる
  final (point, greeting) = givemeSomeDoubles();
  print(point);
  print(greeting);
}

// (double, String)は、タプルというもので、複数の値を返すことができる
(double, String) givemeSomeDoubles() {
  return (4.5, 'Hey');
}	

名前付き引数を使う方法もあります

void main() {
  final values = givemeSomeDoubles();
  // このように、名前付き引数を使っている場合は、.pointや.greetingというように、
  // 変数名の前に.をつけて、変数名を指定することで、値を取り出すことができる
  print(values.point);
  print(values.greeting);
}

// ({double point, String greeting})は、名前付き引数を使っている
({double point, String greeting}) givemeSomeDoubles() {
  return (point: 4.5, greeting: 'Hey');
}

分割代入といえば、Dartでも全く同じことしてるような書き方もありました

void main() {
  final values = [1, 2, 3, 4, 5];
  // この変数は、valuesの要素を順番に取り出す
  final [a, b, c, d, e] = values;
  print(a);
  print(b);
  print(c);
  print(d);
  print(e);
  // この変数は、valuesの最初の要素を取り出す。
  // ...は、残りの要素をリストとして取り出す。ログを見たいので、...の後にhという変数名をつけている。
  final [f, g, ...h] = values;
  print(f);
  print(g);
  print(h);
}

ifにcase文が付いた機能も追加された?

JSONのデータを用意して、実験しました。これもしデータの型が違うとエラーが出ます。switch文にもbreakつけなくても使うことができるようになってるポイです?

void main() {
  // JSONのダミーデータ
  final jsoned = {
    "name": "John",
    "age": 30,
    "body": "My name is John and I am 30 years old."
  };
  // if caseとは、if文の条件式にパターンマッチを使えるようにしたもの
  // もしデータの型が違ったときは、elseの方が実行される
  if(jsoned case {'name': String name, 'age': int age, 'body': String b}) {
    print(name);
    print(age);
    print(b);
  } else {
    print('error');
  }
  switch(jsoned) {
    case {'name': String name, 'age': int age, 'body': String b}:
      print(name);
      print(age);
      print(b);
    default:
      print('error');
  }
}

実行結果

John
30
My name is John and I am 30 years old.
John
30
My name is John and I am 30 years old.

型のエラーが出た場合

まとめ

base, final ,sealedを使ってみましたが、これ難しくて、クラスを継承したものにもキーワードとしてつけないと使えないのですが、sealedだけ継承しているクラスにつけたら、エラー吐いちゃいましたね?
こちらはまだまだ使いこなすのに、時間がかかりそうです。

書いてみたコード

// Validatorクラスは、errorLogメソッドを持っている
// baseをクラスにつけることで、このファイルはbase.dartというライブラリに属することを示している
// baseをつけると継承に使うクラスの使用を制限できる
base class Validator {
  void errorLog() {
    print('error');
  }
}

sealed class Fuga {
  void errorLog() {
    print('error');
  }
}

// finalをつけることで、このクラスを継承することを禁止している
final class Hoge {
  void errorLog() {
    print('error');
  }
}

// FormValidatorクラスは、Validatorクラスを継承している
final class FormValidator extends Hoge {}

// finalをつけることで、このクラスを継承することを制限している
final class FormValidatorTwo extends Fuga {}

// baseをつけることで、このクラスを継承することを制限している
base class FormValidatorThree extends Validator {}

void main() {
  final formValidator = FormValidator();
  formValidator.errorLog();
  final formValidatorTwo = FormValidatorTwo();
  formValidatorTwo.errorLog();
  final formValidatorThree = FormValidatorThree();
  formValidatorThree.errorLog();
}

Discussion