Null safety in Flutter
2 min readJul 6, 2021
- The null assertion operator(!)
int? couldNull = -1;
int? couldNullFunc() => -2;
List<int?> listHoldsNulls = [0, null, 2];
void main() {
int a = couldNull!; // Hey dart, it could be null but just trust me it isn't
int b = couldNullFunc()!.abs(); // Ter hamaagui ee
int c = listHoldsNulls.first!; // I know what I'm doing
}
- The required keyword
int addThreeValues({
required int first,
required int second,
int third = 0,
}) {
return first + second + third;
}
void main() {
final sum = addThreeValues(
first: 1,
second: 5,
// third: 3,
);
}
- Type promotion via null checks
void main() {
Object a = 'This is a string';
if (a is String) {
print(a.length);
}
String? text;
if (DateTime.now().hour < 12) {
text = 'a';
} else {
text = 'b';
}
print(text.length);
print(getLength('This is a string'));
}
int getLength(String? str) {
if (str == null) {
throw 'Hey, that string was null';
// return 0;
}
return str.length;
}
- Object properties aren’t promotable
import 'dart:math';
class StrProvider {
String? get value =>
Random()
.nextBool() ? 'string' : null;
String? b = 'Hello';
}
class StrProviderFactory {
static StrProvider getProvider() => StrProvider();
}
void printStr(String str) => print(str);
void main() {
final provider = StrProvider();
final str = provider.value;
if (str == null) {
print('null');
} else {
print('not null');
printStr(str);
}
if (provider.value == null) {
print('null');
} else {
print('not null');
printStr(provider.value!);
}
if (provider.b == null) {
print('null');
} else {
print('not null');
printStr(provider.b!);
}
final pr = StrProviderFactory.getProvider();
final s = pr.value;
if (s == null) {
print('null');
} else {
print('not null');
printStr(s);
}
}
- The late keyword
class Meal {
late String desc; // Trust me dart desc will be fine. it will never null
void setDesc(String str) {
desc = str;
}
}
void main() {
final meal = Meal();
meal.setDesc('Tuna fish');
print(meal.desc);
}
- late circular references
class Team {
late final Coach coach;
}
class Coach {
late final Team team;
}
void main() {
final team = Team();
final coach = Coach();
team.coach = coach;
coach.team = team;
}
- Late and lazy
int _computeValue() {
print('In _computeValue…');
return 3;
}
class CachedValueProvider {
// final _cache = _computeValue(); // Immadiately
late final _cache = _computeValue(); // Just delay, it is not really null safety related
int get value => _cache;
}
void main() {
print('Calling constructor…');
var provider = CachedValueProvider();
print('Getting value…');
print('The value is ${provider.value}!');
}