Knowledge Test Score Board
— · 0%
Work through the questions below — your score updates as you go.
Keep going · grade bands mapped to DCU's honours scale
Only your first attempt at each question counts toward this score. Reload the page to reset.
This section contains 20 interactive knowledge checks designed to test your understanding of the materials covered in Chapter 7. The questions cover Rust’s ecosystem, memory management, ownership, borrowing, and custom data types.
Please remember that many of the quizzes have multiple correct answers , and you must select all applicable options to succeed. I have carefully balanced the lengths of the answers, so take your time to evaluate each option thoroughly.
Good luck!
Derek.
Concept Match
Match Rust Core Advantages derekmolloy.ie Drag each definition into its matching concept slot, then click Submit. Tap × to return a placed card to the pool.
Definition Pool
A framework for serialising data with zero runtime overhead via compile-time generation.
Enables Rust to run on bare-metal hardware without an operating system.
Provides a set of traits allowing drivers to be portable across different microcontrollers.
A unified toolchain for building, testing, and managing dependencies securely.
Submit
Which of the following statements correctly describes the role of the Cargo.lock file in a professional Rust project? derekmolloy.ie
It provides a temporary caching mechanism for the compiler to significantly speed up the linking phase.
It ensures reproducible builds by rigorously recording the exact versions of all dependencies used.
It securely stores the project's metadata and manually defined list of required external dependencies.
It configures the user's personal preferences for the rust-analyzer extension within the VS Code editor. Submit Answer
Why is Rust considered to have a distinct advantage over C/C++ regarding memory safety in edge programming? derekmolloy.ie
It forces developers to allocate all complex data structures exclusively on the stack for guaranteed safety.
It utilises a highly optimised runtime garbage collector to automatically reclaim unused memory chunks.
It dynamically checks all pointer arithmetic operations during program execution to prevent overflows.
It enforces strict ownership rules at compile time, eliminating common bugs like use-after-free. Submit Answer
Cargo Build and Check Commands derekmolloy.ie Drag snippets from the pool into the blanks so the program produces the output shown, then click Submit.
1 # Verify that code is syntactically and semantically correct without generating a binary:
2 cargo ·····
3
4 # To compile the project and its dependencies into an executable binary, use:
5 cargo ·····
Available Snippets
compile
verify
test
run
build
check
Submit
Concept Match
Match Ownership and Memory Concepts derekmolloy.ie Drag each definition into its matching concept slot, then click Submit. Tap × to return a placed card to the pool.
Definition Pool
An implicit bitwise duplication for simple types that preserves the source variable.
Re-using a variable name by creating a new binding, potentially altering its underlying type.
The default behaviour where ownership is transferred, invalidating the original variable.
An explicit mechanism for performing a deep copy of heap-allocated data structures.
Submit
Predict the output: Shadowing and Scopes derekmolloy.ie Read the code below, then choose the terminal output it produces and click Submit.
1 fn main() {
2 let x = 5;
3 let x = x + 1;
4 {
5 let x = x * 2;
6 print!("{} ", x);
7 }
8 print!("{}", x);
9 }
Submit Answer
In the context of Rust's memory layout, which of the following statements accurately describes the String type? derekmolloy.ie
It allocates all of its character data directly on the stack to guarantee fast, deterministic access.
It is a 24-byte fat pointer on the stack containing a pointer, length, and capacity, with data on the heap.
It stores UTF-32 encoded characters contiguously on the heap, matching the standard behaviour of C++ strings.
It operates as a thin pointer on the stack that automatically grows its allocation during compilation. Submit Answer
Drag snippets from the pool into the blanks so the program produces the output shown, then click Submit.
1 fn main() {
2 // A Box<i32> is an owning pointer to data on the heap.
3 let b: Box<i32> = Box:: ····· (42);
4 // The pointer itself takes up ····· bytes on a 64-bit machine's stack.
5 }
Submit
How do Rust's strict borrowing rules directly prevent data races in concurrent programming? derekmolloy.ie
By transparently copying the underlying data to each thread so they all possess their own local versions.
By requiring developers to manually implement mutexes and locks around every complex data structure.
By enforcing that exactly one mutable reference, or multiple immutable references, exist at any given time.
By automatically pausing all background threads whenever a shared variable is accessed by the main thread. Submit Answer
Drag snippets from the pool into the blanks so the program produces the output shown, then click Submit.
1 // The function signature requires a mutable reference
2 fn modify_text(s: ····· String) {
3 s.push_str(" world");
4 }
5
6 fn main() {
7 // The variable must be declared as mutable to be mutably borrowed
8 let ····· text = String::from("hello");
9 // Pass a mutable reference to the function
10 modify_text( ····· text);
11 }
Submit
What is the primary purpose of lifetimes in Rust's type system? derekmolloy.ie
They ensure that all variables remain active in memory until the main function completes its execution.
They act as a compile-time proof that references will not outlive the underlying data they point to.
They provide a runtime mechanism for the garbage collector to determine when to free allocated memory.
They automatically extend the scope of a stack-allocated variable to prevent it from being dropped. Submit Answer
Concept Match
Match Slices and References derekmolloy.ie Drag each definition into its matching concept slot, then click Submit. Tap × to return a placed card to the pool.
Definition Pool
A non-owning reference to a contiguous sequence of elements within a collection.
A specialised view for UTF-8 data, functioning as a two-word fat pointer.
A pointer to memory that has already been deallocated or gone out of scope.
Compiler rules that automatically infer references' valid scopes to reduce verbosity.
Submit
Implicit Returns and Statements Drag the tiles to arrange the code in the correct order, then click Submit. Locked lines stay in place. Indentation is dynamically applied based on the location of braces.
fn add_and_check(a: i32, b: i32) -> i32 {Submit Order
Drag snippets from the pool into the blanks so the program produces the output shown, then click Submit.
1 fn main() {
2 let mut counter = 0;
3 let result = loop {
4 counter += 1;
5 if counter == 5 {
6 // Halt the loop and return the calculated value
7 ····· counter * 2;
8 }
9 };
10 println!("Result: {}", result);
11 }
Available Snippets
break
return
yield
continue
exit
Submit
Why is Rust's match expression generally considered safer and more robust than a traditional C++ switch statement? derekmolloy.ie
It automatically converts string inputs into their corresponding integer values prior to evaluation.
It entirely prevents the use of integer types, forcing developers to rely exclusively on enumerated types.
It enforces exhaustiveness at compile time, guaranteeing that every possible variant or case is handled.
It dynamically generates fallback branches at runtime to handle unexpected or malformed data inputs. Submit Answer
Which of the following accurately contrasts Rust macros with the C++ preprocessor (#define)? derekmolloy.ie
Rust macros are restricted exclusively to standard library functions and cannot be defined by application developers.
Rust macros execute entirely at runtime, allowing them to dynamically generate code based on user inputs.
Rust macros operate on the Abstract Syntax Tree (AST) and enforce hygiene, preventing accidental name collisions.
Rust macros perform simple textual substitution before compilation, exactly matching the behaviour of the C++ preprocessor. Submit Answer
Concept Match
Match Custom Types and Implementations derekmolloy.ie Drag each definition into its matching concept slot, then click Submit. Tap × to return a placed card to the pool.
Definition Pool
A composite type with named fields, analogous to a standard C++ class or struct.
Defined within an impl block without a self parameter, often functioning as a constructor.
A named collection of unnamed fields that are accessed primarily by their numeric index.
A field-less struct primarily used as a marker type to distinguish different states.
Submit
Drag snippets from the pool into the blanks so the program produces the output shown, then click Submit.
1 enum Command {
2 Move(f64),
3 TurnLeft,
4 }
5
6 fn execute(cmd: Command) {
7 match cmd {
8 // Destructure the f64 data into the distance variable
9 Command::Move( ····· ) => println!("Moving {}", distance),
10 Command::TurnLeft => println!("Turning"),
11 }
12 }
Submit
In the context of edge programming, what is the primary advantage of Rust's default use of static dispatch (monomorphisation)? derekmolloy.ie
It enables maximum runtime flexibility, allowing types to be dynamically swapped during execution.
It drastically minimises the size of the final compiled binary by sharing code across all generic types.
It completely eliminates compilation time overhead by delaying type resolution until the program runs.
It allows the compiler to generate highly optimised, type-specific machine code with zero runtime overhead. Submit Answer
Since Rust does not support traditional class-based inheritance, how does it typically achieve abstraction and polymorphism? derekmolloy.ie
By relying entirely on procedural macros to generate necessary boilerplate code for inherited classes.
By employing smart pointers to dynamically link objects together into a hierarchical memory structure.
By utilising complex C-style unions combined with bitwise operators to emulate object hierarchies.
By defining data structures with structs and specifying shared behaviours and interfaces through traits. Submit Answer
Congratulations on completing the Chapter 7 Knowledge Test!
Review any questions you missed to ensure a solid grasp of Rust’s ownership model, borrowing rules, and custom data types before proceeding.