Type Inference in Rust

Pascal Precht
InstructorPascal Precht
Share this video with your friends

Social Share Links

Send Tweet
Published 4 years ago
Updated 3 years ago

This lesson explains Type Inference in Rust and how it allows the compiler to figure out by itself, what type variables have when they get their values assigned.

There are cases when the compiler cannot infer a value's type through static analysis. In such cases, developers have to provide type annotations explicitly.

Instructor: [00:00] The Rust compiler comes with a feature called type inference. What that means is that it's able to figure out the type of our values without us explicitly annotating things like variables.

[00:11] For example, here we see a variable condition with the value false of type Boolean. We have a variable some_number with the value 5 of type i32. There's another one which is a string slice reference, and we have an array of string slices. All of these variables annotate explicitly their type.

[00:33] We can run this program and we'll see that the compiler is able to compile without any issues. However, even if we go ahead and remove these annotations for most of these variables, we'll see that the compiler is still able to figure out their types.

[00:54] Sometimes however, the compiler is not able to infer the type. This is, for example, the case for APIs like Parse, which lets us parse a string slice to a string. It also allows us to parse the string slice to a number.

[01:13] Since Rust can't know by itself to which type we want to parse to, providing no type annotation at all in this case will cause a compile error. The compiler tells us that we should consider giving the number variable a type.

[01:29] In this particular case, there's two ways to go about this. We can either provide the annotation right after the variable name as we did before. Another way is to use the so-called turbofish syntax, which requires us to put two colons here, followed by an angle bracket, followed by the type, followed by closing angle bracket. Saving this file and running this code, we see that the compiler is happy.

J. Matthew
J. Matthew
~ 4 years ago

I'm curious what is the best practice (if there is one) regarding whether or not to annotate the type explicitly when it's not required by the compiler. I write a lot of TypeScript, and my preference is always to annotate the type even when it could be inferred, for the sake of instant clarity and readability. Take this example:

const isTrueOrFalse: boolean = false;

Here there are multiple indicators of the nature of the variable: 1) The "is" prefix on the name, which conventionally denotes a boolean; 2) The explicit type declaration after the name; 3) The initial value of false. However, it could also be written const myVar = false (or even var myVar = false), and despite the removal of two of those indicators, both the compiler and someone reading the code could easily infer it is a boolean by the initial value. Still, I like including the other indicators, because you don't have to read past the equals sign to understand the variable, and the explicit declaration feels "safer" to me as well (whether it actually is or not, I'm not sure).

I'm sure the answer could vary between languages, but is there a general consensus among Rust developers?

Pascal Precht
Pascal Prechtinstructor
~ 4 years ago

Good question:

I'm curious what is the best practice (if there is one) regarding whether or not to annotate the type explicitly when it's not required by the compiler. I write a lot of TypeScript, and my preference is always to annotate the type even when it could be inferred

So also here, this really depends on your style and probably the conventions you follow alone or with your team. I personally like to look at it this way: If something can be expressed in less characters, it should be expressed in less characters (unless readability suffers from it).

Given the example you just brought up, doing:

const isTrueOrFalse: boolean = false;

Doesn't really add any additional value.

Generally, I think it's good to try to get away with as little annotation as you can and once the compiler complains that it can't infer something, you help out where it's needed.

I'm sure the answer could vary between languages, but is there a general consensus among Rust developers?

I can't really provide an answer that is backed by actual research, but I would assume that most of Rust developers also omit annotations where they aren't necessary (that's what type inference is for after all).

Hope this makes sense!

Markdown supported.
Become a member to join the discussionEnroll Today