Rust Terminologies (Beginner Edition)
Learning something new and coming across specific technical terms that slow your journey always feels frustrating. Don't worry. Everyone faces it, and sometimes, little challenges are needed to make you grow. What's the fun if you know everything?
In this blog, I will share some of the terminologies I faced while learning Rust. These may not cover every terminology in Rust (I don't want to get too technical), but just the ones you may encounter in your beginning stage while learning this unique and versatile language. Also, I'd like to point out that these terms are not Rust-specific, but we will know them in the context of Rust.
System Programming Language
You might have heard about other popular language types, like Procedural, Functional, Object-oriented, and Scripting languages. This unfamiliarity is often why people get intimated by Rust, thinking it's hard to grasp. But the fact is, it just has a different mechanism and can take some time to get used to.
System programming languages are programming languages that are primarily designed for creating system software and low-level applications. System software interacts directly with hardware components and provides essential services to other software applications. These languages are used to develop operating systems, device drivers, compilers, virtual machines, and other software crucial for managing and controlling computer hardware.
Characteristics of system programming languages
Amusing Fact
While looking into different programming languages, you might notice that some languages belong to multiple categories. For example, C++ can be described as a Procedural, Object-oriented, and even system language. There are over 50 programming languages, and most can be classified into multiple language styles.
Expression-based Language
This is another feature I adore about Rust (but only after I knew what it means). Before that, let's learn two sub-terminologies required to understand what expressive language means.
Expression
An expression is a combination of one or more values, variables, operators, and function calls that can be evaluated to produce a single value. Expressions are fundamental building blocks in programming and are used to perform computations, make decisions, and produce results.
let calculated_value: i32 = 20 + (3 * 12);
The above snippet illustrates a simple expression. You can see that the value on the right side is calculated in the runtime and assigned to calculated_values. Function calls can also return an evaluated value, as shown below.
fn calculate_sum(first_number: i32, second_number: i32) -> i32 {
first_number + second_number
}
fn main() {
let sum = calculate_sum(10, 30);
println!("The calculate sum is: {}", sum);
}
Statement
A statement is a single line of code or a group of lines that performs a specific action or task. Statements help in controlling the flow of execution, manipulating data, and interacting with the environment. Unlike expressions, which produce a value, statements are executed for their side effects (action with no return value).
let name: &str = "Bunny";
let age: i32 = 25;
All the lines of code shown above an example of a statement since it performs a specific task without any return value that has been evaluated, as we saw in the expression.
Understanding why Rusty is expression-based
Since we got the idea of expression and statement, we can now discuss how Rust is an expression-based language. But before that, you should keep a few things in mind. Consider the following example:
领英推荐
let name = (let pen_name = "bunny"); // compile-time error
If you observe in the above snippet, pen_name cannot be assigned to the name, and you will get a compile-time error. This is because the variable with the 'let' keyword will not return anything (as we saw in the statement examples). This may not be true for some programming languages like C or Ruby, where name = pen_name = "bunny" is possible.
Now consider this example:
let width = 20;
let height = {
width * 30
}
println!("height is {}", height); // prints 600
In the above example, the block (calculating the height) returns the value 600, which is then assigned to the height variable (without return keyword?). This is possible in Rust since Rust will treat a line without a ';' (semi-colon) as an expression (Rust can throw an error if you are not careful with it).
Also, if you provide a semi-colon at the end of the line, Rust will treat it as a statement. So until you give a semi-colon at the end, Rust will consider it an expression (thus expression-based language).
Statically Typed Language
Another topic with 'language' in it (sigh). Sure, Rust is many things; understanding all these terms will help you comprehend the language better. Statically Typed means that the program needs to know the types of all variables at the compiler time.
1 let age = "25".parse().expect("Not a valid age"); // compile error
2. let age: u32 = "25".parse().expect("Not a valid age") // success
The above example (1) will throw a compile error saying "cannot infer type for '_'. Rust also suggests providing a type for the age variable. This happens because parse() needs to know the type to parse the provided string. This is why example(2) will be successfully assigned the parsed value to age.
Sometimes, providing the type for every variable out there is frustrating. But again, the Rust community learned about this problem and created extensions/plugins for most of the IDE that automatically provides a type for the variable(s) based on the value it holds (sweeeeet).
Shadowing
Shadowing in programming occurs when a variable declared within a specific scope has the same name as a variable declared in an outer scope. As a result, the variable in the inner scope "shadows" or hides the variable in the outer scope. This can lead to confusion and unexpected behaviour, as the inner variable takes precedence over the outer variable within its scope.
Shadowing can be intentional in cases where you want to use the same variable name for a different purpose within a specific scope. For example, consider the following snippet:
let current_password: i32 = 1234;
let current_password: &str = "Rust_Is_Amazing";
println!("{} will open the fortune", current_password);
The above snippet will print "Rust_Is_Amazing" instead of 1234. This is one of those peculiar cases in which you need the same variable name to hold value with different datatypes, as Rust will not allow the same variable to have different data types.
let current_password: i32 = 1234;
current_password = "Rust_Is_Amazing"; // compile error
Unlike other programming languages like Javascript, where the 'let' keyword behaves differently, Rust always preserves(strictly) the type and ownership of a variable.
Rustacean ??
How can I ever miss this term? Rustacean is used to refer to the Rust community. It's a playful and endearing way of identifying with the language and the community. The community is as friendly and cheerful as the crabby you see everywhere when searching for Rust.
Do you know that this crab's name is Ferris, and there is quite a history behind it? Please feel free to look at this forum to learn about it.