Variables in Rust - Rust for TypeScript Developers
Em dashes: 1
Table Of Contents#
- Table Of Contents
- Naming
- Scope
- Initialization
- Declaration
- Redeclaration
- Reassignment
- Mutability
- Outro
Naming#
In Rust, variables are snake cased, while constants are conventially in screaming snake case
const CONSTANT_VALUE: i32 = 2;
let non_constant_value = 32;
Note that variables defined with const must be explicitly typed
Scope#
In Rust, variables are block scoped just like variables declared with let and const in TypeScript
fn main() {
let x = 32;
{
let x = 12;
println!("{x}") // 12
}
println!("{x}") // 32
}
Initialization#
In TypeScript, the initialization of variables declared with var is hoisted
console.log(x); // undefined
var x = 12;
console.log(x); // 12
The initialization of variables declared with let or const is not hoisted
console.log(x);
let x = 12;
Uncaught ReferenceError: can't access lexical declaration 'x' before initialization
However, they are assigned undefined if not given an initializer
let x;
console.log(x); // undefined
Rust takes the more modern behavior of let and const and takes it one step further. Variables are not assigned a value if not given an initializer
This works
fn main() {
let x = 12;
println!("{x}"); // 12
}
This does not
fn main() {
let x: i32;
println!("{x}");
}
error[E0381]: used binding `x` isn't initialized
--> src/main.rs:4:16
|
2 | let x: i32;
| - binding declared here but left uninitialized
|
3 | println!("{x}");
| ^ `x` used here but it isn't initialized
Declaration#
Variables declared with const in Rust can be global, but variables declared with let cannot
So this works,
const X: i32 = 12;
fn main() {
}
But this does not
let x = 12;
fn main() {
}
error: expected item, found keyword `let`
--> src/main.rs:1:1
|
1 | let x = 12;
| ^^^ consider using `const` or `static` instead of `let` for global variables
In TypeScript, variables declared with var, let, or const can be declared anywhere and aren’t required to be explicitly typed
let x = 12;
Redeclaration#
In TypeScript, variables assigned with var can be redeclared locally
var x = 12;
console.log(x); // 12
var x = 32;
console.log(x); // 32
Variables declared with let or const cannot be redeclared locally
const x = 12;
console.log(x);
const x = 32;
console.log(x);
Cannot redeclare block-scoped variable 'x'.
Rust’s const works the same as TypeScript’s in this sense
fn main() {
const X: i32 = 12;
const X: i32 = 12;
}
error[E0428]: the name `X` is defined multiple times
--> src/main.rs:5:3
|
4 | const X: i32 = 12;
| ------------------ previous definition of the value `X` here
5 | const X: i32 = 12;
| ^^^^^^^^^^^^^^^^^^ `X` redefined here
|
= note: `X` must be defined only once in the value namespace of this block
Rust’s let works like var here—it can be redeclared in the same namespace
fn main() {
let x = 12;
println!("{x}"); // 12
let x = 43;
println!("{x}"); // 43
}
However, variables declared with let can be redeclared with a different type!
fn main() {
let x = 32;
println!("{x}");
let x = "hi";
println!("{x}");
}
While in TypeScript, variable declarations can’t change type
var x = 1;
var x = 'hi';
Subsequent variable declarations must have the same type.
Variable 'x' must be of type 'number', but here has type 'string'.
Reassignment#
In TypeScript, variables declared with const cannot be reassigned
const x = 12;
x = 93;
Cannot assign to 'x' because it is a constant.
Variables declared with var or let can be reassigned
let x = 12;
console.log(x); // 12
x = 32;
console.log(x); // 32
In Rust, variables assigned with both let and const cannot be reassigned
fn main() {
let x = 12;
x = 23;
}
error[E0384]: cannot assign twice to immutable variable `x`
--> src/main.rs:6:3
|
4 | let x = 12;
| -
| |
| first assignment to `x`
| help: consider making this binding mutable: `mut x`
5 |
6 | x = 23;
| ^^^^^^ cannot assign twice to immutable variable
Mutability#
As the compiler so kindly pointed out, we can use the mut keyword with let to make x mutable
fn main() {
let mut x = 12;
println!("{x}"); // 12
x = 23;
println!("{x}"); // 23
}
This differs from TypeScript, where objects and arrays are mutable by default
const arr = [];
arr.push(1);
console.log(arr); // [1]
In Rust, this does not compile without the mut keyword
fn main() {
let vec = Vec::new();
vec.push(1);
}
error[E0596]: cannot borrow `vec` as mutable, as it is not declared as mutable
--> src/main.rs:5:3
|
4 | let vec = Vec::new();
| --- help: consider changing this to be mutable: `mut vec`
5 | vec.push(1);
| ^^^^^^^^^^^ cannot borrow as mutable
Outro#
Thank you for reading! Please let me know if you have any suggestions.