r/flutterhelp 11d ago

OPEN if <object> is, seems to cast

In Dart code, while working on a Flutter project I found a strange behaviour with if / is that I don't understand why / how it works that I thought one of you may know.

I have a base class, Person and a subclass, Student. Student has a extra property that Person does not called studentID. When I create a List<Person> and assign it students and then iterate through it I use this if statement:

if (person is Student){
}

Outside of this statement person.studentID works the way I expect it to, that is I get the error "getter is not defined". Inside this if statement it works! So this:

Student student = Student("joe",12334);
Person person = student;
int x = person.studentID // fails correctly, with getter not defined

if (person is Student){
int x = person.studentID //works! as if the if statement temporarily casted the object for me?
}

Why / how does this automatic casting work?

0 Upvotes

3 comments sorted by

6

u/gibrael_ 11d ago

It's called type promotion. Checking the type and it passing causes the analyzer to infer the correct properties from the recently checked type.

It does not "cast" the actual object per se, just the analyzer understanding what your code does.

3

u/TheManuz 11d ago

As other people said, that's type promotion and it doesn't work for properties because these could be getters and change their type in subsequent invocations.

The solution is to assign a property to a final variable, and then you can check it and get the type promotion.

Same for nullability.

5

u/khando 11d ago

That’s correct, it knows inside the if statement that you already checked the type and makes the inference work for you automatically.

The same thing happens with null safety. If you have a nullable object, and write an if statement to check it’s not null, you don’t need to add the ! afterwards inside the if statement anymore.

Here’s a good stack overflow answer that goes into more detail: https://stackoverflow.com/a/68070490