Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add function core::iter::zip #82917

Merged
merged 5 commits into from
Mar 27, 2021
Merged

Add function core::iter::zip #82917

merged 5 commits into from
Mar 27, 2021

Conversation

cuviper
Copy link
Member

@cuviper cuviper commented Mar 8, 2021

This makes it a little easier to zip iterators:

for (x, y) in zip(xs, ys) {}
// vs.
for (x, y) in xs.into_iter().zip(ys) {}

You can zip(&mut xs, &ys) for the conventional iter_mut() and
iter(), respectively. This can also support arbitrary nesting, where
it's easier to see the item layout than with arbitrary zip chains:

for ((x, y), z) in zip(zip(xs, ys), zs) {}
for (x, (y, z)) in zip(xs, zip(ys, zs)) {}
// vs.
for ((x, y), z) in xs.into_iter().zip(ys).zip(xz) {}
for (x, (y, z)) in xs.into_iter().zip((ys.into_iter().zip(xz)) {}

It may also format more nicely, especially when the first iterator is a
longer chain of methods -- for example:

    iter::zip(
        trait_ref.substs.types().skip(1),
        impl_trait_ref.substs.types().skip(1),
    )
    // vs.
    trait_ref
        .substs
        .types()
        .skip(1)
        .zip(impl_trait_ref.substs.types().skip(1))

This replaces the tuple-pair IntoIterator in #78204.
There is prior art for the utility of this in itertools::zip.

@rust-highfive
Copy link
Collaborator

r? @petrochenkov

(rust-highfive has picked a reviewer for you, use r? to override)

@rust-highfive rust-highfive added the S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. label Mar 8, 2021
@cuviper
Copy link
Member Author

cuviper commented Mar 8, 2021

r? @KodrAus

@rust-highfive rust-highfive assigned KodrAus and unassigned petrochenkov Mar 8, 2021
@rust-log-analyzer

This comment has been minimized.

@rust-log-analyzer

This comment has been minimized.

@rust-log-analyzer

This comment has been minimized.

@rust-log-analyzer

This comment has been minimized.

@bluss
Copy link
Member

bluss commented Mar 9, 2021

The main feature is that a free function can have a more permissive trait bound than a method - the method has to have a more specific receiver. The symmetry in the treatment of the two operands contributes to the readability of the code.

  • a.zip(b)
    • a is an iterator and b is an iterable
    • a is receiver and b is a parameter
  • zip(a, b)
    • symmetry: a and b are iterable
    • symmetry: a and b are function parameters
    • (drawback) it's a binary function but it "should be" an n-ary operation with variadic generics

itertools has these "opinonated" free functions (that I introduced there), and the other one I'd speak for would be enumerate(iterable) with similar features to zip.

@cuviper
Copy link
Member Author

cuviper commented Mar 9, 2021

the other one I'd speak for would be enumerate(iterable)

A particular thing I like about that one is that enumerate(iterable) matches the order (index, item), whereas iter.enumerate() reads backwards to me -- a method at the end which adds something to the front.

@bors

This comment has been minimized.

@bors

This comment has been minimized.

@bors

This comment has been minimized.

@bors

This comment has been minimized.

@bors

This comment has been minimized.

@m-ou-se
Copy link
Member

m-ou-se commented Mar 27, 2021

Thanks for working on this, @cuviper!

Can you open a tracking issue? Thanks!

r=me with the tracking issue added.

cc @rust-lang/clippy: this makes minor changes to the clippy code in the last commit.

@m-ou-se m-ou-se added S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. and removed S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. labels Mar 27, 2021
@cuviper cuviper mentioned this pull request Mar 27, 2021
3 tasks
@cuviper
Copy link
Member Author

cuviper commented Mar 27, 2021

Added tracking issue #83574.

@bors r=m-ou-se

@bors
Copy link
Contributor

bors commented Mar 27, 2021

📌 Commit f0a6052 has been approved by m-ou-se

@bors bors added S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. and removed S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. labels Mar 27, 2021
bors added a commit to rust-lang-ci/rust that referenced this pull request Mar 27, 2021
Rollup of 8 pull requests

Successful merges:

 - rust-lang#81351 (combine: stop eagerly evaluating consts)
 - rust-lang#82525 (make unaligned_references future-incompat lint warn-by-default)
 - rust-lang#82626 (update array missing `IntoIterator` msg)
 - rust-lang#82917 (Add function core::iter::zip)
 - rust-lang#82993 (rustdoc: Use diagnostics for error when including sources)
 - rust-lang#83522 (Improve fs error open_from unix)
 - rust-lang#83548 (Always preserve `None`-delimited groups in a captured `TokenStream`)
 - rust-lang#83555 (Add #[inline] to io::Error methods)

Failed merges:

 - rust-lang#83130 (escape_ascii take 2)

r? `@ghost`
`@rustbot` modify labels: rollup
@bors bors merged commit b2e2543 into rust-lang:master Mar 27, 2021
@rustbot rustbot added this to the 1.53.0 milestone Mar 27, 2021
flip1995 pushed a commit to flip1995/rust that referenced this pull request Apr 8, 2021
Add function core::iter::zip

This makes it a little easier to `zip` iterators:

```rust
for (x, y) in zip(xs, ys) {}
// vs.
for (x, y) in xs.into_iter().zip(ys) {}
```

You can `zip(&mut xs, &ys)` for the conventional `iter_mut()` and
`iter()`, respectively. This can also support arbitrary nesting, where
it's easier to see the item layout than with arbitrary `zip` chains:

```rust
for ((x, y), z) in zip(zip(xs, ys), zs) {}
for (x, (y, z)) in zip(xs, zip(ys, zs)) {}
// vs.
for ((x, y), z) in xs.into_iter().zip(ys).zip(xz) {}
for (x, (y, z)) in xs.into_iter().zip((ys.into_iter().zip(xz)) {}
```

It may also format more nicely, especially when the first iterator is a
longer chain of methods -- for example:

```rust
    iter::zip(
        trait_ref.substs.types().skip(1),
        impl_trait_ref.substs.types().skip(1),
    )
    // vs.
    trait_ref
        .substs
        .types()
        .skip(1)
        .zip(impl_trait_ref.substs.types().skip(1))
```

This replaces the tuple-pair `IntoIterator` in rust-lang#78204.
There is prior art for the utility of this in [`itertools::zip`].

[`itertools::zip`]: https://docs.rs/itertools/0.10.0/itertools/fn.zip.html
@cuviper cuviper deleted the iter-zip branch September 21, 2021 16:43
matthiaskrgr added a commit to matthiaskrgr/rust that referenced this pull request Dec 15, 2021
… r=scottmcm

Stabilize `iter::zip`

Hello all!

As the tracking issue (rust-lang#83574) for `iter::zip` completed the final commenting period without any concerns being raised, I hereby submit this stabilization PR on the issue.

As the pull request that introduced the feature (rust-lang#82917) states, the `iter::zip` function is a shorter way to zip two iterators. As it's generally a quality-of-life/ergonomic improvement, it has been integrated into the codebase without any trouble, and has been
used in many places across the rust compiler and standard library since March without any issues.

For more details, I would refer to `@cuviper's` original PR, or the [function's documentation](https://doc.rust-lang.org/std/iter/fn.zip.html).
flip1995 pushed a commit to flip1995/rust that referenced this pull request Dec 17, 2021
… r=scottmcm

Stabilize `iter::zip`

Hello all!

As the tracking issue (rust-lang#83574) for `iter::zip` completed the final commenting period without any concerns being raised, I hereby submit this stabilization PR on the issue.

As the pull request that introduced the feature (rust-lang#82917) states, the `iter::zip` function is a shorter way to zip two iterators. As it's generally a quality-of-life/ergonomic improvement, it has been integrated into the codebase without any trouble, and has been
used in many places across the rust compiler and standard library since March without any issues.

For more details, I would refer to `@cuviper's` original PR, or the [function's documentation](https://doc.rust-lang.org/std/iter/fn.zip.html).
rossmacarthur added a commit to rossmacarthur/rust that referenced this pull request Dec 28, 2022
The addition of `core::iter::zip` (rust-lang#82917) set a precedent for adding
plain functions for iterator adaptors. Adding `chain` makes it a little
easier to `chain` two iterators.

```
for (x, y) in chain(xs, ys) {}
// vs.
for (x, y) in xs.into_iter().chain(ys) {}
```

There is prior art for the utility of this in `itertools::chain`.
compiler-errors pushed a commit to compiler-errors/rust that referenced this pull request Jun 4, 2024
The addition of `core::iter::zip` (rust-lang#82917) set a precedent for adding
plain functions for iterator adaptors. Adding `chain` makes it a little
easier to `chain` two iterators.

```
for (x, y) in chain(xs, ys) {}
// vs.
for (x, y) in xs.into_iter().chain(ys) {}
```
compiler-errors added a commit to compiler-errors/rust that referenced this pull request Jun 4, 2024
…nieu

Add function `core::iter::chain`

The addition of `core::iter::zip` (rust-lang#82917) set a precedent for adding plain functions for iterator adaptors. Adding `chain` makes it a little easier to `chain` two iterators.

```rust
for (x, y) in chain(xs, ys) {}
// vs.
for (x, y) in xs.into_iter().chain(ys) {}
```

There is prior art for the utility of this in [`itertools::chain`](https://docs.rs/itertools/latest/itertools/fn.chain.html).

Approved ACP rust-lang/libs-team#154
GuillaumeGomez added a commit to GuillaumeGomez/rust that referenced this pull request Jun 4, 2024
…nieu

Add function `core::iter::chain`

The addition of `core::iter::zip` (rust-lang#82917) set a precedent for adding plain functions for iterator adaptors. Adding `chain` makes it a little easier to `chain` two iterators.

```rust
for (x, y) in chain(xs, ys) {}
// vs.
for (x, y) in xs.into_iter().chain(ys) {}
```

There is prior art for the utility of this in [`itertools::chain`](https://docs.rs/itertools/latest/itertools/fn.chain.html).

Approved ACP rust-lang/libs-team#154
rust-timer added a commit to rust-lang-ci/rust that referenced this pull request Jun 4, 2024
Rollup merge of rust-lang#106186 - rossmacarthur:ft/iter-chain, r=Amanieu

Add function `core::iter::chain`

The addition of `core::iter::zip` (rust-lang#82917) set a precedent for adding plain functions for iterator adaptors. Adding `chain` makes it a little easier to `chain` two iterators.

```rust
for (x, y) in chain(xs, ys) {}
// vs.
for (x, y) in xs.into_iter().chain(ys) {}
```

There is prior art for the utility of this in [`itertools::chain`](https://docs.rs/itertools/latest/itertools/fn.chain.html).

Approved ACP rust-lang/libs-team#154
lcnr pushed a commit to lcnr/rust that referenced this pull request Jun 12, 2024
The addition of `core::iter::zip` (rust-lang#82917) set a precedent for adding
plain functions for iterator adaptors. Adding `chain` makes it a little
easier to `chain` two iterators.

```
for (x, y) in chain(xs, ys) {}
// vs.
for (x, y) in xs.into_iter().chain(ys) {}
```
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-iterators Area: Iterators S-waiting-on-bors Status: Waiting on bors to run and complete tests. Bors will change the label on completion. T-libs-api Relevant to the library API team, which will review and decide on the PR/issue.
Projects
None yet
Development

Successfully merging this pull request may close these issues.