From 51ae1b324cd73fdb4fe3695b5d483a44b4aff4a9 Mon Sep 17 00:00:00 2001 From: jfecher Date: Mon, 21 Oct 2024 14:19:38 -0500 Subject: [PATCH] fix: Allow array map on empty arrays (#6305) # Description ## Problem\* Resolves a private issue sent to me on slack ## Summary\* Array map is a fairly old method written before we had `std::mem::zeroed`. Now that we have zeroed, we can allow mapping empty arrays since we can use `zeroed` to get the filler `U` value for the starting elements. ## Additional Context While I was at it I included a small clarification to `reduce`'s docs that it requires a non-empty array ## Documentation\* Check one: - [ ] No documentation needed. - [x] Documentation included in this PR. - [ ] **[For Experimental Features]** Documentation to be submitted in a separate PR. # PR Checklist\* - [x] I have tested the changes locally. - [x] I have formatted the changes with [Prettier](https://prettier.io/) and/or `cargo fmt` on default settings. --- docs/docs/noir/concepts/data_types/arrays.md | 2 ++ noir_stdlib/src/array/mod.nr | 15 ++++++++++++--- 2 files changed, 14 insertions(+), 3 deletions(-) diff --git a/docs/docs/noir/concepts/data_types/arrays.md b/docs/docs/noir/concepts/data_types/arrays.md index bb68e60fe53..289145a8c4d 100644 --- a/docs/docs/noir/concepts/data_types/arrays.md +++ b/docs/docs/noir/concepts/data_types/arrays.md @@ -203,6 +203,8 @@ fn main() { Same as fold, but uses the first element as the starting element. +Requires `self` to be non-empty. + ```rust fn reduce(self, f: fn(T, T) -> T) -> T ``` diff --git a/noir_stdlib/src/array/mod.nr b/noir_stdlib/src/array/mod.nr index 46acf619dd2..f5089de1877 100644 --- a/noir_stdlib/src/array/mod.nr +++ b/noir_stdlib/src/array/mod.nr @@ -43,10 +43,10 @@ impl [T; N] { /// assert_eq(b, [2, 4, 6]); /// ``` pub fn map(self, f: fn[Env](T) -> U) -> [U; N] { - let first_elem = f(self[0]); - let mut ret = [first_elem; N]; + let uninitialized = crate::mem::zeroed(); + let mut ret = [uninitialized; N]; - for i in 1..self.len() { + for i in 0..self.len() { ret[i] = f(self[i]); } @@ -79,6 +79,8 @@ impl [T; N] { } /// Same as fold, but uses the first element as the starting element. + /// + /// Requires the input array to be non-empty. /// /// Example: /// @@ -217,3 +219,10 @@ impl From> for [u8; N] { s.as_bytes() } } + +mod test { + #[test] + fn map_empty() { + assert_eq([].map(|x| x + 1), []); + } +}