Start learning free

LESSON 150 OF 414 · LOOPS & GLOBAL VARIABLES

Counting Occurrences in an Array in Rust: A Simple for Loop

Practice Read the full explanation

Given an array of integers nums, count and return the number of occurrences of a given value.

Example:

Input: nums = [1, 4, 2, 2, 5, 2], value = 2
Output: 3
Explanation: the value 2 appears 3 times in the array

Note:

Do not use builtin functions, it would defy the purpose of the challenge. Write the whole code yourself.

STEP 1 OF 4
    Ctrl + Enter to check

    RUST · LOOPS & GLOBAL VARIABLES

    Array Count in Rust, explained

    Problem overview

    The function count takes a vector of integers, nums, and an integer value. It returns how many times value appears in nums.

    For nums = [1, 4, 2, 2, 5, 2] and value = 2, the 2 appears at three positions, so the result is 3. If the value does not appear at all, the result is 0.

    The task is to write the loop yourself and not to rely on a ready-made helper. This is the counting pattern, which shows up in many later problems.

    Approach

    Look at every element once. Keep a counter that starts at 0, and each time an element equals value, add 1 to it. After the last element, the counter is the answer.

    Elements that differ from value are skipped. The order of the elements does not matter, and neither does what the other values are, so there is no need to sort or to remember anything beyond the counter.

    On the example, the counter goes 0, then stays at 0 for 1 and 4, rises to 1 at the first 2, rises to 2 at the second, stays at 2 for 5, and reaches 3 at the last 2.

    Step by step

    1. Declare the counter. let mut count = 0; creates it as mutable, because it changes inside the loop. Without mut, count += 1 would not compile.
    2. Loop over a reference to the vector. for n in &nums borrows the vector. Looping over nums directly would move the vector into the loop.
    3. Compare with value. Iterating by reference gives n the type &i32. Rust does not compare a &i32 with an i32, so the condition writes *n == value, where *n reads the number behind the reference.
    4. Increment on a match. Inside the if, count += 1 adds one. Rust has no ++ operator.
    5. Return after the loop. The return goes outside the loop, so it runs only after every element has been checked.

    The solution in Rust

    impl Solution {
        fn count(nums: Vec<i32>, value: i32) -> i32 {
            let mut count = 0;
            for n in &nums {
                if *n == value {
                    count += 1;
                }
            }
            return count;
        }
    }
    

    Some Rust details here:

    • References and *. &nums is a borrowed view of the vector, and iterating over it yields references to the elements. The dereference *n turns a &i32 back into an i32 for comparison.
    • Why borrowing is useful. A for loop over nums would consume the vector. Here the function owns nums anyway and nothing uses it afterwards, so either would compile, but borrowing is the habit that carries over to functions that need the vector later.
    • Same name for variable and function. The local count has the same name as the method count. This is legal, because the function is always reached through Solution::count and never by the bare name count, so the variable does not hide it.
    • Type inference. The compiler makes count an i32, since the function returns i32.
    • No ++. Use count += 1.

    Complexity

    Time: O(n). Each of the n elements is compared once. Skipping or counting an element takes constant time.

    Space: O(1). The function keeps only the counter and the loop variable.

    Edge cases and common mistakes

    • An empty vector. The loop does not run, and the result is 0.
    • A value that never appears. The counter stays at 0. count(vec![1, 1], 3) returns 0.
    • A vector made only of the value. count(vec![2, 2, 2], 2) returns 3.
    • Returning inside the loop. A return count; placed in the loop body would end the function after the first element.
    • Setting instead of adding. Writing count = 1; in the if records only that the value was seen, not how many times.
    • Comparing a reference with a number. n == value fails to compile, because &i32 and i32 are different types. Dereference with *n.

    Testing

    • nums = [1, 4, 2, 2, 5, 2], value = 2 gives 3.
    • nums = [], value = 2 gives 0.
    • nums = [1, 1], value = 3 gives 0.
    • nums = [7], value = 7 gives 1.
    Keep going with RustAbout 340 step-by-step lessons, from your first line of code to coding interviews. Free to start.
    Start learning free