Basics
Print your Name N times using recursion
fn solve(i:i32, n:i32){
if i==n{
return;
} else {
println!("hello");
solve(i+1, n);
}
}
fn main() {
solve(0,3);
}
Print from 1 to N using Recursion
fn solve(i:i32, n:i32){
if i==n{
return;
} else {
println!("{}", i);
solve(i+1, n);
}
}
fn main() {
solve(0,3);
}
Printing integers from N to 1 (using Backtracking)
fn solve(i:i32, n:i32){
if i==n{
return;
} else {
solve(i+1, n);
println!("{}", i);
}
}
fn main() {
solve(0,3);
}
Recursive way of calculating the sum of first N Natural Numbers:
-
Parameterized Way
fn solve(i:i32, sum:i32){ if i==0{ println!("{}", sum); return; } else { solve(i-1, sum+i); } } fn main() { solve(5,0); }
-
Functional Way
fn solve(i:i32) -> i32 { if i==0{ return 0; } else { return i + solve(i-1); } } fn main() { println!("{}", solve(5)); }
Reverse an array
fn main() {
let mut v = vec![1, 2, 3, 4, 5];
v.reverse();
println!("{:?}", v);
}
Given String is Palindrome or not
use basics::*;
fn main() {
let input = take_string_as_vec();
let mut ispalin = true;
let mut ptr1= 0;
let mut ptr2 = input.len()-1;
let mut i = 0;
while i<=(input.len()>>1) {
if input[ptr1] != input[ptr2] {
ispalin = false;
break
}
ptr1+=1;
ptr2-=1;
i+=1;
}
println!("{}", ispalin);
}
HashMap (unordered map)
Rust uses ahash
by default
Given an array of integers: [1, 2, 1, 3, 2] and we are given some queries: [1, 3, 4, 2, 10]. For each query, we need to find out how many times the number appears in the array.
use std::collections::HashMap;
fn main() {
let arr = vec![1, 2, 1, 3, 2];
let queries = vec![1, 3, 4, 2, 10];
let mut freq_map = HashMap::<i32, usize>::new();
for num in arr {
*(freq_map.entry(num).or_insert(0)) += 1;
}
for query in queries {
let result = freq_map.get(&query);
let mut count=0;
match result {
Some(&num) => count = num,
None => count = 0
}
println!("{} appears {} times", query, count);
}
// Instead of matching the Option returned from get we could have used
// unwrap but it doesn't work on &{integer} so we can use .copied() that
// converts and `Option<&usize>` into `Option<usize>`
for query in queries {
let count = freq_map.get(&query).copied().unwrap_or(0);
println!("{} appears {} times", query, count);
}
}
Given an array of size N. Find the highest and lowest frequency element. can use Moore’s Voting Algorithm too to find highest frequency element
use std::collections::HashMap;
fn main() {
let arr = vec![1, 2, 1, 3, 2];
let mut freq_map = HashMap::<i32, usize>::new();
for num in arr {
*freq_map.entry(num).or_insert(0) += 1;
}
let mut min_freq = usize::MAX;
let mut max_freq = usize::MIN;
let mut min_ele = 0;
let mut max_ele = 0;
for (&num, &count) in &freq_map {
if count < min_freq {
min_freq = count;
min_ele = num;
}
if count > max_freq {
max_freq = count;
max_ele = num;
}
}
for key_value in &freq_map {
println!("{} appears {} times", *key_value.0, *key_value.1);
}
println!("Maximum frequency element is {} with {} frequency", max_ele, max_freq);
println!("Minimum frequency element is {} with {} frequency", min_ele, min_freq);
}
Sorting
Rust uses TimSort by default which takes O(nlogn)
Selection Sort
use basics::*;
fn main() {
let mut arr = take_vector_int();
let n = arr.len();
for i in 0..n {
let mut min = i;
for j in i+1..n {
if arr[j] < arr[i] {
min = j;
}
}
let temp = arr[i];
arr[i] = arr[min];
arr[min] = temp;
}
for i in arr{
print!("{} ", i);
}
}
Bubble sort
use basics::*;
fn main() {
let mut arr = take_vector_int();
let n = arr.len();
for i in 0..n {
for j in i+1..n {
if arr[j] < arr[j-1] {
let temp = arr[j];
arr[j] = arr[j-1];
arr[j-1] = temp;
}
}
}
for i in arr{
print!("{} ", i);
}
}
Insertion Sort
use basics::*;
fn main() {
let mut arr = take_vector_int();
let n = arr.len();
for i in 1..n {
if arr[i] < arr[i-1] {
for j in (1..=i).rev() {
if arr[j] < arr[j-1] {
let temp = arr[j];
arr[j] = arr[j-1];
arr[j-1] = temp;
}
}
}
}
for i in arr{
print!("{} ", i);
}
}
Merge Sort
pub fn merge_sort(arr:Vec<usize>) -> Vec<usize>{
let len = arr.len();
if len <=1 {
return arr
}
let mid = len/2;
let arr1 = merge_sort(arr[..mid].to_vec());
let arr2 = merge_sort(arr[mid..].to_vec());
merge(arr1, arr2)
}
pub fn merge(arr1:Vec<usize>, arr2:Vec<usize>) -> Vec<usize> {
let mut arr3 = Vec::<usize>::new();
let mut i = 0;
let mut j = 0;
while i < arr1.len() && j < arr2.len(){
if arr1[i] < arr2[j] {
arr3.push(arr1[i]);
i+=1;
} else {
arr3.push(arr2[j]);
j+=1;
}
}
arr3.extend_from_slice(&arr1[i..]);
arr3.extend_from_slice(&arr2[j..]);
arr3
}
fn main() {
let arr = take_vector_int();
let sorted = merge_sort(arr);
for i in sorted{
print!("{} ", i);
}
}
Arrays
Check for rotated sorted array
pub fn check(nums: Vec<i32>) -> bool {
let mut drop_count = 0;
let l = nums.len();
for i in 0..l {
if nums[i] > nums[(i + 1) % l] {
drop_count += 1;
}
}
let is_sorted_or_rotated = drop_count <= 1;
is_sorted_or_rotated
}
remove duplicates
pub fn remove_duplicates(nums: &mut Vec<i32>) -> i32 {
let l = nums.len();
let mut i = 0;
for j in 1..l{
if nums[i] != nums[j]{
i += 1;
nums[i] = nums[j];
}
}
(i+1) as i32
}
rotate array by k places:
pub fn rotate(nums: &mut Vec<i32>, k: i32) {
let var = k as usize;
let l = nums.len();
let r = (var % l);
let temp = nums[(l-r)..].to_vec();
nums.truncate(l-r);
nums.splice(0..0, temp);
}
move zeros to end:
let mut left = 0;
for right in 0..nums.len() {
println!("{}, {}", left, right);
if nums[right] != 0 {
nums.swap(left, right);
left += 1;
}
println!("{:?}", nums);
}
find missing number in a range
pub fn missing_number(nums: Vec<i32>) -> i32 {
let l = nums.len();
let mut xor1 = 0;
let xor2 = match l%4 {
0 => l,
1 => 1,
2 => l + 1,
_ => 0,
} as i32;
for i in nums {
xor1 ^= i;
}
xor1^xor2
}
Using prefix sum array, subarray with maximum sum, return sum
pub fn max_sub_array(nums: Vec<i32>) -> i32 {
let l = nums.len();
if l == 1{
return nums[0]
}
let mut sums:Vec<i32> = vec![0; l];
sums[0] = nums[0];
for i in 1..l {
sums[i] = sums[i-1]+nums[i];
}
let mut max_ele = sums[0];
let mut min_ele = 0;
for i in sums {
max_ele = max_ele.max(i-min_ele);
min_ele = min_ele.min(i);
}
return max_ele
}
Kadane’s Algorithm for subarray with maximum sum, return sum
pub fn max_sub_array(nums: Vec<i32>) -> i32 {
let l = nums.len();
let mut max = nums[0];
let mut sum = nums[0];
for i in 1..l{
sum = sum.max(0) + nums[i];
max = max.max(sum);
}
return max
}
Two Sum, sum of two elements in an array is equal to target
use std::collections::HashMap;
impl Solution {
pub fn two_sum(nums: Vec<i32>, target: i32) -> Vec<i32> {
let l = nums.len();
let mut pos = Vec::new();
let mut map = HashMap::new();
for i in 0..l {
map.insert(nums[i], i);
}
for i in 0..l {
match map.get(&(target-nums[i])) {
Some(value) => {
if *value!= i {
pos.push(i as i32);
pos.push(*value as i32);
break
}
},
None => {}
}
}
pos
}
}
Dutch National flag algorithm, Sort an array of 0’s 1’s and 2’s
pub fn sort_colors(nums: &mut Vec<i32>) {
let l = nums.len();
let mut low = 0;
let mut mid = 0;
let mut high = l-1;
while mid<=high {
if nums[mid] == 0{
nums.swap(low, mid);
mid += 1;
low += 1;
} else if nums[mid] == 1 {
mid += 1;
} else {
nums.swap(mid, high);
if high !=0 {
high -= 1;
} else {
break
}
}
}
}
Moore’s Voting Algorithm, majority element
pub fn majority_element(nums: Vec<i32>) -> i32 {
let l = nums.len();
let mut ele = nums[0];
let mut cnt = 1;
for i in 1..l {
if cnt == 0 {
ele = nums[i];
cnt += 1;
} else {
if nums[i] == ele {
cnt += 1;
} else {
cnt -= 1;
}
}
}
ele
}
Next Permutation
let mut nums = take_vector_int();
let l = nums.len();
// Step 1: Find the break point:
let mut ind = l + 1; // break point
for i in (0..l - 2).rev() {
if nums[i] < nums[i + 1] {
println!("{}, {}", nums[i], nums[i + 1]);
ind = i;
break;
}
}
// If break point does not exist means we are at highest permutation:
if ind == l+1 {
nums.reverse();
} else {
println!("{}, {}", ind, nums[ind]);
// Step 2: Find the next greater element
// and swap it with arr[ind]:
for i in (0..l - 1).rev() {
if nums[i] > nums[ind] {
nums.swap(ind, i);
println!("{:?}", nums);
break;
}
}
// Step 3: reverse the right half:
nums[ind + 1..].reverse();
}
println!("{:?}", nums);
Longest Consecutive Subsequence
use basics::*;
use std::collections::HashSet;
fn main() {
let mut nums = take_vector_int();
let l = nums.len();
let mut set = HashSet::new();
for i in 0..l {
set.insert(nums[i]);
}
println!("{:?}", set);
let mut longest = 0;
let mut cnt = 1;
for &i in &set {
if !set.contains(&(i-1)){
let mut j = i+1;
loop {
if set.contains(&j) {
cnt += 1;
j += 1;
} else {
longest = longest.max(cnt);
cnt = 1;
break
}
}
}
}
longest = longest.max(cnt);
println!("{}", longest);
}
Rotate a square matrix 90 = transpose + reverse row 180 = reverse row + reverse col 270 = transpose + reverse col for 90 :
let mut matrix = [[5,1,9,11],[2,4,8,10],[13,3,6,7],[15,14,12,16]];
let l = matrix.len();
// Transpose of a matrix
for i in 0..l {
for j in i+1..l {
println!("{}, {}", i, j);
let temp = matrix[i][j];
matrix[i][j] = matrix[j][i];
matrix[j][i] = temp;
}
}
println!("{:?}", matrix);
// Reverse the rows
for i in 0..l/2 {
let k = l-1-i;
println!("{}", k);
for j in 0..l {
println!("{}, {} swap with {}, {}", j, i, j, k);
let temp = matrix[j][i];
matrix[j][i] = matrix[j][k];
matrix[j][k] = temp;
}
}
println!("{:?}", matrix);
Spiral matrix
pub fn spiral_order(matrix: Vec<Vec<i32>>) -> Vec<i32> {
let m = matrix.len();
let n = matrix[0].len();
let mut ans = Vec::new();
let mut top = 0;
let mut right = n-1;
let mut bottom = m-1;
let mut left = 0;
while top <= bottom && left <= right {
for i in left..=right {
ans.push(matrix[top][i]);
}
top += 1;
for i in top..=bottom {
ans.push(matrix[i][right]);
}
if right == 0 { break; }
right -= 1;
if top <= bottom {
for i in (left..=right).rev() {
ans.push(matrix[bottom][i]);
}
if bottom == 0 { break; }
bottom -= 1;
}
if left <= right {
for i in (top..=bottom).rev() {
ans.push(matrix[i][left]);
}
left += 1;
}
}
ans
}
Pascal’s Triangle
pub fn generate(num_rows: i32) -> Vec<Vec<i32>> {
let mut ans = Vec::<Vec<i32>>::new();
for row in 1..=num_rows as usize {
ans.push(vec![1]);
let mut ele = 1;
for col in 1..row {
ele = ele*(row-col);
ele = ele/col;
ans[row-1].push(ele as i32);
}
}
ans
}
Extended Boyer Moore’s Voting Algorithm
use std::i32::MIN;
impl Solution {
pub fn majority_element(nums: Vec<i32>) -> Vec<i32> {
let l = nums.len();
let mut ans = Vec::new();
let mut cnt1 = 0;
let mut cnt2 = 0;
let mut ele1 = MIN;
let mut ele2 = MIN;
for i in 0..l {
if cnt1==0 && ele2!=nums[i] {
ele1 = nums[i];
cnt1 = 1;
} else if cnt2==0 && ele1!=nums[i] {
ele2 = nums[i];
cnt2 = 1;
} else if ele1 == nums[i] {
cnt1+=1;
} else if ele2 == nums[i] {
cnt2+=1;
} else {
cnt1-=1;
cnt2-=1;
}
}
cnt1 = 0;
cnt2 = 0;
for i in 0..l{
if nums[i] == ele1 {
cnt1+=1;
}
if nums[i] == ele2 {
cnt2+=1;
}
}
if cnt1 > l/3 {
ans.push(ele1);
}
if cnt2 > l/3 {
ans.push(ele2);
}
ans
}
}
3 Sum, using 3 pointers
let mut nums = take_vector_int();
let l = nums.len();
let mut ans = Vec::<Vec<i32>>::new();
nums.sort();
let mut i = 0;
while i<l-2 {
let mut j = i+1;
let mut k = l-1;
if i>0 && nums[i] == nums[i-1] {
i += 1;
} else {
while j<k {
let sum = nums[i]+nums[j]+nums[k];
if sum < 0 {
j+=1;
} else if sum > 0 {
k-=1;
} else {
ans.push(vec![nums[i], nums[j], nums[k]]);
j+=1;
k-=1;
while j<k && nums[j] == nums[j-1] {
j+=1;
}
while j<k && nums[k] == nums[k+1] {
k-=1;
}
}
}
i+=1;
}
}
println!("{:?}", ans);
4 Sum, using 4 pointer (similar to 3 Sum)
pub fn four_sum(mut nums: Vec<i32>, target: i32) -> Vec<Vec<i32>> {
let l = nums.len();
let mut ans = Vec::<Vec<i32>>::new();
if l<4 {
return ans;
}
if l == 4 {
let mut sum:i64 = 0;
for i in 0..4 {
sum += nums[i] as i64;
}
if sum == target as i64 {
ans.push(vec![nums[0], nums[1], nums[2], nums[3]]);
}
return ans;
}
nums.sort();
let mut i = 0;
while i<l-3 {
let mut j = i+1;
if i>0 && nums[i] == nums[i-1]{
i+=1;
} else {
while j < l-2 {
let mut k = j+1;
let mut m = l-1;
if j>i+1 && nums[j] == nums[j-1] {
j += 1;
} else {
while k<m {
let sum:i64 = (nums[i]+nums[j]+nums[k]+nums[m]) as i64;
if sum < target as i64 {
k+=1;
} else if sum > target as i64 {
m-=1;
} else {
ans.push(vec![nums[i], nums[j], nums[k], nums[m]]);
k+=1;
m-=1;
while k<m && nums[k] == nums[k-1] {
k+=1;
}
while k<m && nums[m] == nums[m+1] {
m-=1;
}
}
}
j+=1;
}
}
i+=1;
}
}
ans
}
Length of the longest subarray with zero Sum
use basics::*;
use std::collections::HashMap;
fn main() {
let mut nums = take_vector_int();
let l = nums.len();
let mut max = 0;
let mut sum = 0;
let mut map = HashMap::<i32, usize>::new();
for i in 0..l{
sum += nums[i];
if sum == 0 {
max = i+1;
} else {
if let Some(&idx) = map.get(&sum) {
max = max.max(i-idx);
} else {
map.insert(sum, i);
}
}
}
println!("{}", max);
}
Count the number of subarrays with given xor K
let mut arr = take_vector_int();
let mut k = take_int();
let l = arr.len();
let mut map = HashMap::<i32, usize>::new();
let mut cnt = 0;
let mut x = 0;
for i in 0..l {
x ^= arr[i];
if x == k {
cnt+=1;
} else {
if let Some(&c) = map.get(&(x^k)) {
cnt+=c;
} else {
*map.entry(x).or_insert(0) += 1;
}
}
}
println!("{}", cnt);
XOR Queries of a Subarray
pub fn xor_queries(arr: Vec<i32>, queries: Vec<Vec<i32>>) -> Vec<i32> {
let l = arr.len();
let mut x = Vec::<i32>::new();
x.push(arr[0]);
for i in 1..l {
x.push(x[i-1]^arr[i]);
}
let mut ans = Vec::new();
for q in queries {
if q[0] == 0 {
ans.push(x[q[1] as usize]);
} else {
ans.push( x[q[1] as usize]^x[(q[0]-1) as usize] )
}
}
ans
}