Open4
Flutterでfreezedを使うときに知っておきたかったTips
説明書を読まずにゲームを始めるタイプなので、freezedを使っていて
- あれ、こういうことしたいんだけどfreezedだと出来ないのかな? → 公式ドキュメントや技術記事調べる → できるやん!
を何度かやったので、備忘録としてまとめる。
freezedでインスタンスを返す
例えば、2分間、と言うデータを表すのに、
- Firebaseではintで管理 ( int 2)している
- しかし、freezedなオブジェクトから受け取るときは、getterを使って
Duartion()
の形で受け取りたい
といった場合。
abstract class Task with _$Task {
factory Task({
int minutes,
})=_Task;
Duration get duration => Duration(minutes:minutes);
}
とやると次のようなエラーが出る。
Error Getters not decorated with @late requires a MyClass._() constructor
指摘通り、次のように@late
をつければ解決する。
abstract class Task with _$Task {
factory Task({
int minutes,
})=_Task;
Duration get duration => Duration(minutes:minutes);
}
freezedであるオブジェクトの派生オブジェクトを作る
個人的にはif文を増やしたくないので、できればあるオブジェクトの詳細なタイプをフラグ管理するようなことはしたくない。
例えば、次のように、その文房具がペンか消しゴムかを、stationeryType
を読んで判断することをしたくない。
// 文房具を表すクラス
abstract class Stationery with _$Stationery {
factory Stationery({
// Pen or Eraser
String stationeryType,
String name,
int price,
Color color,
})=_Stationery;
}
こういう時は、次のようにする。
abstract class Stationery with _$Stationery {
factory Stationery.pen({
String name,
int price,
Color color,
}) = Pen;// 外部からもPenを読み取れるように、`_`を外す
factory Stationery.eraser({
String name,
int price,
}) = Eraser;// Eraserも同様に`_`を外す
}
こうしておくと、次のようにオブジェクトが何かによって処理を分けることもできる。
final stationery = Stationery.pen(
name:'普通のペン',
price:100,
color:Colors.black,
);
stationery.map(
pen:(Pen pen)=>print('This is a pen.'),
eraser:(Eraser eraser)=>print('This is a eraser.'),
);
freezedでnullable
例えば、連結リストのような構造を作るとき、next
やprev
は基本必須パラメータにしたいが、先頭と末尾のみはnull
を許容したい。といったケースがある。
ただ、普通に@required
すると、null
を入れた時にエラーが出る。
abstract class Item with _$Item {
factory Item({
String id,
Item next,
Item prev,
}) = _Item;
こうした時は、@nullable
をつけておく。
abstract class Item with _$Item {
factory Item({
String id,
Item next,
Item prev,
}) = _Item;
連結リスト①(単方向・線形) | Programming Place Plus アルゴリズムとデータ構造編【データ構造】 第3章