diff --git a/Cargo.toml b/Cargo.toml index 7ff3046..da30973 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -4,3 +4,4 @@ version = "0.1.0" edition = "2021" [dependencies] + diff --git a/README.md b/README.md index 3aabe99..b5dbe51 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,149 @@ -# Rust Sessions -Intro to primitives \ No newline at end of file +1. Difference Between fp32 and fp64 Data Types +In Rust, floating-point numbers can be represented by two types + +f32: 32-bit floating-point number +f64: 64-bit floating-point number + Key Differences +Bit Size: +f32 uses 32 bits to represent a number. +f64 uses 64 bits, which allows for more precision and a larger range. + +Precision: +f32 gives you approximately 7 decimal digits of precision. +f64 gives you approximately 15-16 decimal digits of precision + +f32 = 1.1234567; // 7 decimal places, limited precision +f64 = 1.1234567891234567; // 15-16 decimal places, high precision + + +Range: +f32 can represent numbers between 1.4 x 10^-45 to 3.4 x 10^38. +f64 can represent numbers between 5.0 x 10^-324 to 1.8 x 10^308 + +Memory Usage: +f32 uses less memory (4 bytes). +f64 uses double the memory (8 bytes). + +When to Use: +we can use f32 when performance and memory efficiency are important and precision isn’t critical (e.g., graphics, gaming, some ML models). +we can use f64 when higher precision or a larger range is needed (e.g., scientific computations, financial calculations). + + +2. Role of Pointers in Memory Management in Rust +In Rust, pointers are crucial for memory management, but unlike languages like C or C++, Rust provides safe memory management through its ownership model, ensuring that most pointer issues (like dangling pointers, null pointers, etc.) are handled at compile-time. + + Key Points About Pointers in Rust + + +Memory Address: +In Rust, pointers store the memory address of a variable. These are like references to variables stored elsewhere in memory, allowing you to directly manipulate the data. + +let x = 10; +let y = &x; // `y` is a pointer to `x` +println!("The value of x is: {}", x); // Accessing value of `x` directly + +Dynamic Memory Allocation: +Rust automatically manages dynamic memory through its ownership model, but can be manually allocate using Box, Rc (reference-counted), and Arc (atomic reference-counted) for heap-allocated data. + +Efficient Data Access: +By using references (essentially pointers) in Rust, data can be passed around efficiently without being copied. +let s = String::from("Hello"); +let t = &s; // Borrowing a reference to `s` +println!("{}", t); // Access data without copying + +Pass-by-Reference: +Rust uses references (&T) and mutable references (&mut T) to allow functions to modify variables without making copies. + +Pointer Arithmetic: +Rust does not allow pointer arithmetic in safe code. This prevents mistakes like buffer overflows and out-of-bounds access. + + +Memory Management: +Rust uses a borrow checker and ownership system to prevent memory leaks. When a variable goes out of scope, Rust automatically deallocates memory (destruction) without needing explicit free() or delete() commands. + + +in summary Pointers in Rust are used to reference data in memory efficiently without copying. +Rust’s ownership and borrowing system ensures memory safety, and dynamic memory allocation is done using Box, Rc, Arc, and other structures. +Rust doesn’t allow pointer arithmetic in safe code to prevent common errors (e.g., buffer overflows), but you can use unsafe blocks if necessary, although they should be used with caution. + + + +difference between &str and string + +&str: This is a string slice, which is an immutable reference to a portion of a string. It does not own the data it references; instead, it borrows the data from another source, such as a String or a string literal. &str is lightweight and useful when you only need to view a part of a string without owning it. It is commonly used for function parameters when you do not need to modify the string. + +String: This is a growable, heap-allocated, UTF-8 encoded string. It owns its data and can be modified and resized at runtime. You can create a new String by calling String::new() or by converting from a string slice using to_string(). String is mutable and can be used in scenarios where you need to build or modify strings dyn + + + + + + + + +A CPU, or Central Processing Unit, is the primary component in a computer that executes instructions and processes data from computer programs. It acts as the “brain” of the computer, handling tasks such as arithmetic, logic, and input/output operations. The CPU coordinates other components in the system and is essential for the computer’s overall functionality. + +RAM (Random Access Memory) + +Temporary, fast memory that stores: + +Currently running programs,Active data being processed,Operating system components + + +Characteristics: + +Volatile (loses data when power is off) +Much faster than storage drives +Directly accessible by CPU +Measured in GB (8GB, 16GB, etc.) + + + +ROM (Read-Only Memory) + +Permanent memory that contains: + +BIOS/UEFI (Basic Input/Output System) +Firmware +Boot instructions + + +Characteristics: + +Non-volatile (keeps data when power is off) +Can't be easily modified +Slower than RAM +Usually small capacity + + + +How They Work Together: + +ROM stores startup instructions +When computer starts, CPU reads ROM instructions +Operating system loads into RAM +CPU processes instructions, using RAM as working memory +Data flows between components via system bus + + +A stack is a part of memory that has a specific data structure. + +When there is a new piece of data that should be stored, the stack will always put it “on top”. (push to the stack) +When a piece of data should be removed from the stack, it is also taken “from the top”. (pop off the stack) +using the last in, first out (LIFO) data structure. +All entries that are pushed to the stack are required to have a known, fixed size. The size should be known at compile time, and can not change during runtime. We can not put things of variable size in the stack (like a string that might grow in size). + + + heap + +Heap memory in Rust is a part of the memory system used for dynamic memory allocation. Unlike stack memory, which is managed automatically by the compiler and has a fixed layout, heap memory is managed manually and is not bound to function scopes. This means that variables allocated on the heap can live longer than the function that created them, allowing for more flexible memory managem + + +A pointer is a general concept for a variable that contains an address in memory. This address refers to, or “points at,” some other data. + + +anything not implemented by a vetor dont have capacity + + + + diff --git a/src/calculator.rs b/src/calculator.rs new file mode 100644 index 0000000..c767e23 --- /dev/null +++ b/src/calculator.rs @@ -0,0 +1,53 @@ +struct Calculator { + value: f64, +} + +impl Calculator { + fn new() -> Calculator { + Calculator { + value: 5.0 + } + } + + fn add(&mut self, number: f64) -> f64 { + self.value += number; + self.value + } + + fn subtract(&mut self, number: f64) -> f64 { + self.value -= number; + self.value + } + + fn multiply(&mut self, number: f64) -> f64 { + self.value *= number; + self.value + } + + + fn divide(&mut self, number: f64) -> Result { + if number == 0.0 { + return Err(String::from("Cannot divide by zero!")); + } + self.value /= number; + Ok(self.value) + } + +} + + + +pub fn cal() { + let mut calc = Calculator::new(); + + println!("Adding 5: {}", calc.add(10.0)); + println!("Multiplying by 2: {}", calc.multiply(2.0)); + println!("Subtracting 3: {}", calc.subtract(3.0)); + + + match calc.divide(2.0) { + Ok(result) => println!("Dividing by 2: {}", result), + Err(error) => println!("Error: {}", error), + } +} + diff --git a/src/char.rs b/src/char.rs new file mode 100644 index 0000000..ea1fcb7 --- /dev/null +++ b/src/char.rs @@ -0,0 +1,22 @@ + +pub fn name(x: char, y: char) -> String { + let mut name = String::new(); + name.push(x); + name.push(y); + name +} + + pub fn myname(x: &str, y: &str) -> String { + let mut myname = String::new(); + myname.push_str(x); + myname.push_str(y); + myname +} + +pub fn intro_to_char() { + let name_result: String = name('D', 'o'); + println!("The char result is: {}", name_result); + + let myname_result: String = myname("Darey", "Olowo"); + println!("my name are : {}", myname_result); +} \ No newline at end of file diff --git a/src/f64operation.rs b/src/f64operation.rs new file mode 100644 index 0000000..3ea6d8f --- /dev/null +++ b/src/f64operation.rs @@ -0,0 +1,18 @@ +// Floating-point Types + +pub fn add(x: f64, y: f64) -> f64 { + x + y +} + +pub fn minus(x: f64, y: f64) -> f64 { + x - y +} + +pub fn rise(x: f64, y: f64) -> f64 { + x * y +} + +pub fn split(x: f64, y: f64) -> f64 { + x / y +} + diff --git a/src/main.rs b/src/main.rs index 3cc3d3e..0779738 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,24 +1,125 @@ +mod u8operation; +mod f64operation; +mod char; +mod signed_integers; +mod calculator; + fn main() { - intro_to_u(); + // intro_to_u(); + // intro_to_f(); + // crate::char::intro_to_char(); + // convert_high(); + // convert_high_to_low(); + // crate::signed_integers::perform_operations(); + crate::calculator::cal(); + } -// function to encapsulate all integers + + + + + + + + + + + + + + + + + + + + +// function to encapsulate all integers and to check for even numbers fn intro_to_u() { - let sum_result: u8 = sum(5, 10); - println!("the sum result is: {}", sum_result); + let sum_result: u8 = u8operation::sum(5, 20); + println!("the sum result is: {}", sum_result); + println!( + "Is the sum result even? {}", + if crate::u8operation::is_even(sum_result) { "Yes" } else { "No" } + ); + + let subtract_result: u8 = u8operation::subtract(20, 15); + println!("the subtract result is: {}", subtract_result); + println!( + "Is the subtract result even? {}", + if crate::u8operation::is_even(subtract_result) { + "Yes" + } else { + "No" + } + ); + let multiply_result: u8 = u8operation:: multiply(5, 12); + println!("the multiply result is {}", multiply_result); + println!( + "Is the multiply result even? {}", + if crate::u8operation::is_even(multiply_result) { + "Yes" + } else { + "No" + } + ); + let divide_result: u8 = u8operation::divide(20, 4); + println!("the divide result is {}", divide_result); + println!( + "Is the divide result odd? {}", + if crate::u8operation::is_odd(divide_result) { "Yes" } else { "No" } + ); } -fn sum(x: u8, y: u8) -> u8 { - x + y // implicit return -// return x + y; // explicit return + + + + + +// functions for Floating points + +fn intro_to_f() { + let add_result: f64 = f64operation::add(10.3.into(), 10.1.into()); + println!("the add result is: {}", add_result); + + let minus_result: f64 = f64operation::minus(25.5.into(), 5.5.into()); + println!("the subract2 result is: {}", minus_result); + + let rise_result: f64 = f64operation::rise(5.2.into(), 3.7.into()); + println!("the multiply2 result is {}", rise_result); + + let split_result: f64 = f64operation::split(30.9.into(), 2.3.into()); + println!("the divide result is {}", split_result); } -// subtract -// multiplication -// division + + + + + +// how to convert u8 to u32 + +fn convert_high() { + let low: u8 = 255; + let high: u32 = low as u32; + println!("u8 value: {}, u32 value:{}", low, high); +} +//Function to convert high bit integer to low bit integer u32 to u8 + +fn convert_high_to_low() { + let high: u32 = 300; + let low: u8 = high as u8; + println!("u32 value: {}, u8 value: {}", high, low); +} + + + + + diff --git a/src/signed_integers.rs b/src/signed_integers.rs new file mode 100644 index 0000000..f164815 --- /dev/null +++ b/src/signed_integers.rs @@ -0,0 +1,22 @@ + +//Implement arithmetic operations on signed integers + +pub fn perform_operations() { + let a: i32 = 25; // A signed 32-bit integer + let b: i32 = -10; // Another signed 32-bit integer + + // Arithmetic operations + let sum = a + b; + let difference = a - b; + let product = a * b; + let quotient = a / b; + let remainder = a % b; // Modulus (remainder) + + println!("Arithmetic Operations on signed integers:"); + println!("a = {}, b = {}", a, b); + println!("Sum: {}", sum); + println!("Difference: {}", difference); + println!("Product: {}", product); + println!("Quotient: {}", quotient); + println!("Remainder: {}", remainder); +} \ No newline at end of file diff --git a/src/u8operation.rs b/src/u8operation.rs new file mode 100644 index 0000000..3cfbd5b --- /dev/null +++ b/src/u8operation.rs @@ -0,0 +1,36 @@ +pub fn sum(x: u8, y: u8) -> u8 { + x + y // implicit return + // return x + y; // explicit return +} + + + +// subtract + +pub fn subtract(x: u8, y: u8) -> u8 { + return x - y; +} + +// multiplication + + pub fn multiply(x: u8, y: u8) -> u8 { + x * y +} +// division + + pub fn divide(x: u8, y: u8) -> u8 { + x / y +} + +// function to check for even numbers + +pub fn is_even(x: u8) -> bool { + x % 2 == 0 +} + +// to check for odd nummbers + +pub fn is_odd(x: u8) -> bool { + x % 2 != 0 +} +