DZone
Thanks for visiting DZone today,
Edit Profile
  • Manage Email Subscriptions
  • How to Post to DZone
  • Article Submission Guidelines
Sign Out View Profile
  • Post an Article
  • Manage My Drafts
Over 2 million developers have joined DZone.
Log In / Join
Refcards Trend Reports
Events Video Library
Refcards
Trend Reports

Events

View Events Video Library

Zones

Culture and Methodologies Agile Career Development Methodologies Team Management
Data Engineering AI/ML Big Data Data Databases IoT
Software Design and Architecture Cloud Architecture Containers Integration Microservices Performance Security
Coding Frameworks Java JavaScript Languages Tools
Testing, Deployment, and Maintenance Deployment DevOps and CI/CD Maintenance Monitoring and Observability Testing, Tools, and Frameworks
Culture and Methodologies
Agile Career Development Methodologies Team Management
Data Engineering
AI/ML Big Data Data Databases IoT
Software Design and Architecture
Cloud Architecture Containers Integration Microservices Performance Security
Coding
Frameworks Java JavaScript Languages Tools
Testing, Deployment, and Maintenance
Deployment DevOps and CI/CD Maintenance Monitoring and Observability Testing, Tools, and Frameworks

Modernize your data layer. Learn how to design cloud-native database architectures to meet the evolving demands of AI and GenAI workkloads.

Secure your stack and shape the future! Help dev teams across the globe navigate their software supply chain security challenges.

Releasing software shouldn't be stressful or risky. Learn how to leverage progressive delivery techniques to ensure safer deployments.

Avoid machine learning mistakes and boost model performance! Discover key ML patterns, anti-patterns, data strategies, and more.

Related

  • Rust’s Ownership and Borrowing Enforce Memory Safety
  • Mastering Ownership and Borrowing in Rust
  • From Zero to Meme Hero: How I Built an AI-Powered Meme Generator in React
  • Singleton: 6 Ways To Write and Use in Java Programming

Trending

  • The Modern Data Stack Is Overrated — Here’s What Works
  • A Guide to Container Runtimes
  • Breaking Bottlenecks: Applying the Theory of Constraints to Software Development
  • Unlocking AI Coding Assistants Part 3: Generating Diagrams, Open API Specs, And Test Data
  1. DZone
  2. Coding
  3. Languages
  4. Rust Programming Language: A Beginner’s Guide

Rust Programming Language: A Beginner’s Guide

Rust was created by Mozilla for Firefox and is used by major companies like Facebook, Apple, Amazon, Microsoft, and Google.

By 
Beste Bayhan user avatar
Beste Bayhan
·
Jan. 23, 24 · Analysis
Likes (2)
Comment
Save
Tweet
Share
4.6K Views

Join the DZone community and get the full member experience.

Join For Free

In our workplace, we took on a challenge as front-end developers to delve into Rust and explore how we can create web applications. The initial step was familiarizing ourselves with the language’s fundamentals by studying the documentation. Upon initiating my study of Rust, I recognized similarities between Rust and JS/TS, drawing these was important for me to facilitate a more intuitive understanding. I wanted to share my learning path, writing this article outlining my exploration of Rust from the perspective of a front-end developer.

The Rust programming language was originally developed by Mozilla for Firefox, and it is also used in major companies such as Facebook, Apple, Amazon, Microsoft, and Google. Notable projects like Dropbox, npm, GitHub, and Deno leverage Rust too. Also, the compiler of Next.js “Turbopack” has contributed to a remarkable 94.7% increase in speed in Next.js version 14.

Why the Rust programming language is gaining popularity can be attributed to several key factors. Firstly, Rust is a compiled language that generates efficient machine code. This characteristic ensures that applications developed with Rust deliver exceptional performance. Moreover, Rust is highly reliable due to its compiler, which effectively prevents undefined behavior that might otherwise result in unexpected outcomes or crashes.

Another one is its memory efficiency. While many languages either manage memory automatically, like JavaScript’s garbage collector, or have complete control over memory management, as in C or C++, Rust introduces a unique approach called the ownership model. (We will get back to this topic later.)

In the upcoming sections of this article, we will explore essential topics of the Rust programming language from the perspective of a front-end developer. These topics include data types, variables, mutability, functions, tuples, arrays, structs, references, and borrowing.

Rust Programming Language

Data Types

The contrast between JavaScript and the Rust programming language primarily manifests in their approach to data types. JavaScript adopts a dynamic typing system, while Rust employs static typing. In Rust, it is a must to determine the types of all variables at compile time, a characteristic that aligns more closely with TypeScript.

Every value in Rust is associated with a specific data type, and these types are categorized into two main groups: Scalar and Compound types. In contrast, JS/TS has a small set of data types such as numbers, strings, booleans, and objects. Scalar types in Rust include integers (both signed and unsigned), floating-point numbers, booleans, and characters, while compound types comprise tuples and arrays. 

Integers

A notable distinction in data types is that, unlike JS/TS, Rust provides size-specific choices for integers and floating-point numbers. This allows you to precisely regulate the amount of memory allocated for each type. Consequently, Rust stands out for its memory efficiency and high performance.

Rust

Floating Numbers

Rust offers two floating point types: f32 and f64, with sizes of 32 bits and 64 bits. The default type is f64 because it provides a similar speed to f32, offering more precision. It’s important to note that all floating-point types in Rust are signed.

 
let x = 5.8;


Booleans

In Rust, like in JS/TS, the Boolean type has two potential values: true and false. They are one byte in size, and it is denoted by bool.

 
let isRustReliable = true;
let isRustReliable: bool = true;


Characters

Rust’s char type is four bytes in size. It specifically represents a Unicode Scalar Value, allowing it to encompass a broader range of characters beyond ASCII. This includes accented letters, different alphabet characters, emojis, and zero-width spaces, making Rust’s char type more versatile in handling diverse character sets.

 
let char_type = 'a'
let char_type: char = 'A';


Tuples

A tuple groups together a variety of types into one compound type. Tuples come with a predetermined length, and once declared, they are unable to expand or delete. 

 
let origin: (i8, u8, f64) = (-5, 2, 2.2)
let (a,b,c) = origin; // destructuring in tuple
let firstElement = origin.0; // indexing


Arrays

Arrays, in contrast to tuples, require each of their elements to share the same type. Unlike arrays in JS/TS, Rust arrays have a fixed length, making it impossible to add or remove elements directly. If dynamic resizing is needed, similar to arrays in JS/TS, Vectors in Rust would likely be the suitable alternative.

 
let origin: [i8, 3] = [1, 2, 3];
let origin = [4; 3] // means [4,4,4]
let first = origin[0];


Variables and Mutability

In Rust, the default behavior for variables is immutability, meaning that their values cannot be changed once assigned. The let keyword is used to declare variables, and if you want a mutable variable, you need to explicitly use mut after let.

 
// Immutable variable
let x = 5;
// Mutable variable
let mut y = 10;
y = 15; // Valid because y is mutable


There are also constants too, and one notable distinction between let is that you cannot use mut with constants. Constants, unlike variables, are inherently immutable. They are declared using the const keyword, and their type must be explicitly annotated. 

 
const MULTIPLIER: u32 = 5;


Constants can be declared in any scope, including the global scope, making them valuable for values shared across different parts of the code.

Functions

In the Rust programming language, function bodies consist of a series of statements and optionally end in an expression. Statements are instructions that perform actions but do not return a value, while expressions evaluate to a resultant value. 

 
fn main() {
    let y = {
        let x = 3; // statement
        x + 1 // expression, which evaluates the value assigned to y
    };


    println!("The value of y is: {y}");
}


In JavaScript, you can create functions using either function declarations or expressions. In Rust, you can use function declarations or lambda functions, known as closures, each with its own syntax and distinctive features.

 
JS

// Function Declaration
function add(a, b) {
  return a + b;
}

// Function Expression
const subtract = function(a, b) {
  return a - b;
};

Rust

// Function Declaration
fn add(a: i32, b: i32) -> i32 {
    a + b
}

// Closure (Lambda Function)
let subtract = |a: i32, b: i32| -> i32 {
    a - b
};


Ownership, References, and Borrowing

Ownership is a fundamental concept in the Rust programming language that establishes a set of rules governing how the language manages memory throughout the program’s execution. In JavaScript, memory management is typically handled by a garbage collector, which automatically reclaims memory that is no longer in use, relieving developers of explicit memory management responsibilities. Unlike Rust, JavaScript’s abstraction of memory details makes it well-suited for high-level development but sacrifices fine-grained control over memory allocation and deallocation.

The stack, organized as a first-in, first-out (FIFO) fixed-size structure, contrasts with the heap, an unbounded and less organized memory space with an unknown size at compile time. Rust’s memory allocator dynamically locates an available space in the heap, designates it as in use, and returns a pointer representing the address of that location.

Key ownership rules in Rust include that each value can have only one owner, the value is dropped from memory when the owner goes out of scope, and there can be only one owner at any given time. 

In Rust, the automatic memory management is facilitated by the drop function, which is called when a variable goes out of scope.

 
rust
{
 // `s` is not valid here; it’s not yet declared
 let s = "hello"; // `s` is valid from this point forward


 // do stuff with `s`
} // this scope is now over, and `s` is no longer valid
                 // this scope is now over, and s is no longer valid


Rust uses references, denoted by the & symbol, allowing you to refer to a value without taking ownership of it. References ensure that the data they point to remains valid for the duration of the reference’s lifetime.

 
let original = String::from("hello");
let reference = &original; // 


Rust’s references are immutable by default, meaning they cannot modify the data they point to. However, mutable references, denoted by &mut, allow modifications to the referenced data.

 
let mut value = 42;
let reference = &mut value; // Mutable reference to `value`


// Modify `value` through the mutable reference
*reference = 10;


A significant restriction on mutable references is that if you have one, you cannot have any other references—mutable or immutable—to the same value.

 
let mut s = String::from("hello");
let r1 = &mut s;
let r2 = &mut s; // ERROR: Cannot have multiple mutable references to `s`


This restriction prevents data races at compile time. Data races occur when multiple pointers access the same data concurrently; at least one of them modifies the data, and there’s no synchronization mechanism.

 
// In Rust, you cannot mix mutable and immutable references.
let s = String::from("hello");
let r1 = &s;    // No problem
let r2 = &s;    // No problem
let r3 = &mut s; // BIG PROBLEM: Cannot have a mutable reference alongside immutable references


The Rust programming language enforces the rule that you can either have one mutable reference or any number of immutable references to a value—this is the principle of exclusive mutable or shared immutable references.

Compiled language JavaScript Memory (storage engine) Rust (programming language) Data Types Computer programming

Published at DZone with permission of Beste Bayhan. See the original article here.

Opinions expressed by DZone contributors are their own.

Related

  • Rust’s Ownership and Borrowing Enforce Memory Safety
  • Mastering Ownership and Borrowing in Rust
  • From Zero to Meme Hero: How I Built an AI-Powered Meme Generator in React
  • Singleton: 6 Ways To Write and Use in Java Programming

Partner Resources

×

Comments

The likes didn't load as expected. Please refresh the page and try again.

ABOUT US

  • About DZone
  • Support and feedback
  • Community research
  • Sitemap

ADVERTISE

  • Advertise with DZone

CONTRIBUTE ON DZONE

  • Article Submission Guidelines
  • Become a Contributor
  • Core Program
  • Visit the Writers' Zone

LEGAL

  • Terms of Service
  • Privacy Policy

CONTACT US

  • 3343 Perimeter Hill Drive
  • Suite 100
  • Nashville, TN 37211
  • [email protected]

Let's be friends: