# [swift-evolution] Add a while clause to for loops

Wed Jun 8 10:40:36 CDT 2016

```IMO `.prefix` is just not the equal alternative for as proposed `while` :
in case of 'while' expression `number < 4_000_000` will be calculated
*only* for those who `number % 2 == 0`. In case of `prefix` - the
expression will be processed for each `number` and only after this filtered
by `number % 2`. Let's assume we need to check for some
veryExpensiveTest(number):

for number in fibonacci where number % 2 == 0 while
veryExpensiveTest(number) {}

let numbers = fibonacci.prefix { veryExpensiveTest(\$0) }
for number in numbers where number % 2 == 0 {}

So, `while` for `for` loops just can't be always replaced with `prefix`

On 08.06.2016 2:02, Xiaodi Wu via swift-evolution wrote:
> On Tue, Jun 7, 2016 at 5:11 PM, Tim Vermeulen <tvermeulen at me.com
> <mailto:tvermeulen at me.com>> wrote:
>
>     most sense to evaluate these clauses from left to right. However, cases
>     where the order matters are very uncommon, and I would rather have the
>     power to choose which clause is evaluated first than to have a forced
>     default order. Either way I don’t see this as a reason not to allow
>     combining the two clauses because IMO it can lead to some very clean
>     code. For instance, say we want to loop through all even fibonacci
>     numbers below 4 million  (see problem #2 from project euler), we could
>     do this:
>
>     `for number in fibonacci where number % 2 == 0 while number < 4_000_000
>     { }`
>
>
> This statement looks like spaghetti to me. I would not at all support
> extending the language to permit it. Do you really think it's more readable
> than going step-by-step?
>
> ```
> let numbers = fibonacci.prefix { \$0 < 4_000_000 }
> for number in numbers where number % 2 == 0 {
>   // ...
> }
> ```
>
> or just:
>
> ```
> let numbers = fibonacci.prefix { \$0 < 4_000_000 }
> let evens = numbers.filter { \$0 % 2 == 0 }
> for number in evens {
>   // ...
> }
> ```
>
>
>     I could have ordered the two clauses in any way I want. If combining
>     the clauses weren’t allowed, I’d have to put (at least) one of them
>     inside the block, which would be a (minor) pain.
>
>     I don’t currently have a very strong opinion about the order of
>     evaluation, so I might be convinced otherwise. But combining the two
>     clauses is so powerful that I don’t think it’s worth to get rid of just
>     because of an edge case.
>
>     > It may be workable if you can have only one or the other, but mixing and matching them as proposed above would be a world of hurt:
>     >
>     > ```
>     > for foo in bar where condition1 while condition2 { ... }
>     > ```
>     >
>     > If condition1 and condition2 both evaluate to true, then whether you continue or break would depend on the relative order of where and while; for generality, you would want to allow both `for...in...where...while` and `for...in...while...where`, and likely `for...in...while...where...while`, etc. There is nothing in the meaning of those words that would suggest that `while...where` behaves differently from `where...while`, etc. This is why words like "break" and "continue" are IMO far superior.
>     >
>     >
>     > On Tue, Jun 7, 2016 at 2:34 PM, Erica Sadun<erica at ericasadun.com
>     > >
>     > > > On Jun 7, 2016, at 1:16 PM, Tim Vermeulen via swift-evolution<swift-evolution at swift.org
>     <mailto:swift-evolution at swift.org>(mailto:swift-evolution at swift.org
>     <mailto:swift-evolution at swift.org>)>wrote:
>     > > > > The meaning of the proposed while is not at all a pair for where, since where clauses in while loops would do the same thing as while clauses in for loops. That's crazy.
>     > > >
>     > > > It sounds crazy, but it’s the nature of the while loop. A where clause in a while loop also has a different result than a where clause in a for loop.
>     > >
>     > > The where_clause appears in the for in statement
>     > >
>     > > for_in_statement : 'for' 'case'? pattern 'in' expression where_clause? code_block
>     > >
>     > > It's syntactic sugar because the expression can be already be limited through functional chaining of some sort or another. At the same time, it's nice and pleasant to have `where` and I'm not itching to throw it out. The same courtesy could be easily extend to `when` (because I don't really want to use the `while` keyword here, but I could easily be convinced otherwise because I don't have a strong stance either way):
>     > >
>     > > for_in_statement : 'for' 'case'? pattern 'in' expression (where_clause | when_clause)? code_block
>     > > when_clause : 'when' expression
>     > >
>     > > and again it could be nice and pleasant to have, although not necessary. The question comes down to how much does the language benefit by this sugar.
>     > >
>     > > I'd say that in both cases, combining chaining and statements is
>     marginallyless goodthan either using standalone chaining or statements
>     without chaining. But as I say this, I know as a fact, I fully intend
>     to use `sequence(_:, next:).take(while:)` with for0in statements, so
>     I'm starting from a hypocritical vantage point.
>     > >
>     > > To summarize, I'm more +0.01 than I am -0.01 on this.
>     > >
>     > > -- E
>     > > p.s. Sorry, wux
>     > >
>     > >
>     >
>     >
>     >
>
>
>
>
> _______________________________________________
> swift-evolution mailing list
> swift-evolution at swift.org
> https://lists.swift.org/mailman/listinfo/swift-evolution
>
```