We can't find the internet
Attempting to reconnect
Something went wrong!
Attempting to reconnect
← Rust: zero to hero step 3 of 342
Naming conventions and the style gate
Return the sum of a slice and the number of elements in it.
pub fn summarize_scores(raw_scores: &[i32]) -> (i32, usize)
The contract
raw_scoresmay be empty. An empty slice returns(0, 0).- Values may be negative. The first tuple element is the arithmetic sum of every value, and the second is the slice length.
- The tests keep every value and every total inside the
i32range, so you do not need to handle overflow. (If a sum did overflow, a debug build would panic and a release build would wrap around, unless overflow checks were configured differently.)
Examples: [10, 20, 30] returns (60, 3), and [100, -100, 0] returns
(0, 3).
Why the correct starter still fails
The starter returns the right answer for every test, but it does not pass
the site's Rust style check. That check runs Clippy, Rust's linter, with
-D warnings. A lint is a compiler check that reports suspicious or
unidiomatic code without the code being invalid. Most lints are warnings by
default; -D warnings turns every warning into an error. Clippy runs the
normal compiler too, so this flag denies rustc's built-in lints in addition
to Clippy's extra ones.
The starter triggers five different lints and six diagnostics in total.
Four of the lints come from rustc itself.
non_snake_case (reported twice, for TotalSum and Count). Rust's
naming conventions are checked by warn-by-default lints. Variables and
functions use snake_case. Types, traits and enum variants use
UpperCamelCase (checked by non_camel_case_types). Constants and statics
use SCREAMING_SNAKE_CASE (checked by non_upper_case_globals). Ordinary
compilation only warns about a name like TotalSum; here the warning
becomes an error. For acronyms, the convention treats the acronym as one
word: HttpResponse, not HTTPResponse. Clippy's upper_case_acronyms
lint enforces part of this, but by default it only reports names that are
entirely uppercase, such as struct HTTP, and only on items that are not
part of a public API.
unused_variables (score_limit). The variable is assigned and never
read. If you deliberately want to keep an unused binding, start its name
with an underscore, such as _score_limit. The compiler does not report
unused bindings whose names start with _. Usually the better fix is to
delete the binding.
unused_mut (result). The binding is declared mut but never
changed. Removing mut tells readers that the value stays the same.
dead_code (average). A private function that nothing calls. In a
larger crate this lint often finds code left behind after a refactor. In
this exercise, the helper is not part of the answer, so delete it.
The fifth lint comes from Clippy.
clippy::let_and_return (let mut result = ...; result). The block
stores a value in a binding only to return that binding on the next line.
Return the expression directly instead: (TotalSum, Count) in place of the
last two lines.
Fixing the starter
You can fix each diagnostic in place: rename the two variables, delete
score_limit, return the tuple directly and delete average. A loop that
accumulates the sum and count is acceptable to the gate once those changes
are made.
There is also a shorter version. The slice already knows its length
(.len()), and an iterator over the values can be summed with .sum().
Writing the body with those two methods leaves no accumulators, counter or
temporary binding to cause lints, though average still has to be deleted.
Suppressing a lint
Sometimes a warning is intentional, for example a helper you are keeping for later. You can mark the item instead of changing the code:
#[allow(dead_code)]turns the lint off for that item.#[expect(dead_code)](stable since Rust 1.81) also suppresses it, but reports anunfulfilled_lint_expectationswarning if the lint stops firing, for example after the function starts being called. Under-D warningsthat report is also an error, so the annotation cannot stay in place after it is no longer needed.
Try deleting or fixing the code first. A suppression is for cases where the warned-about code is deliberate.
The return type
(i32, usize) is a tuple, a fixed-size group of values of possibly
different types. Here it lets the function return two values without
defining a struct. usize is the unsigned integer type Rust uses for
lengths and indexes. Its width matches the target's pointer size: 8 bytes on
64-bit targets and 4 bytes on 32-bit targets. .len() on a slice already
returns a usize, so the count needs no conversion.
Your code, saved here
Sign in to access your accepted solutions and saved draft history. You can keep reading the lesson without an account.
Sign in to your accountStuck?
Rust reference solution
Sign in to track your attempts toward unlocking the reference solution.