@@ -308,22 +308,22 @@ where
308
308
I : Iterator ,
309
309
{
310
310
a : I ,
311
- a_cur : Option < I :: Item > ,
311
+ a_cur : Option < Option < I :: Item > > ,
312
312
b : J ,
313
313
b_orig : J ,
314
314
}
315
315
316
316
/// Create a new cartesian product iterator
317
317
///
318
318
/// Iterator element type is `(I::Item, J::Item)`.
319
- pub fn cartesian_product < I , J > ( mut i : I , j : J ) -> Product < I , J >
319
+ pub fn cartesian_product < I , J > ( i : I , j : J ) -> Product < I , J >
320
320
where
321
321
I : Iterator ,
322
322
J : Clone + Iterator ,
323
323
I :: Item : Clone ,
324
324
{
325
325
Product {
326
- a_cur : i . next ( ) ,
326
+ a_cur : None ,
327
327
a : i,
328
328
b : j. clone ( ) ,
329
329
b_orig : j,
@@ -339,24 +339,33 @@ where
339
339
type Item = ( I :: Item , J :: Item ) ;
340
340
341
341
fn next ( & mut self ) -> Option < Self :: Item > {
342
- let elt_b = match self . b . next ( ) {
342
+ let Self {
343
+ a,
344
+ a_cur,
345
+ b,
346
+ b_orig,
347
+ } = self ;
348
+ let elt_b = match b. next ( ) {
343
349
None => {
344
- self . b = self . b_orig . clone ( ) ;
345
- match self . b . next ( ) {
350
+ * b = b_orig. clone ( ) ;
351
+ match b. next ( ) {
346
352
None => return None ,
347
353
Some ( x) => {
348
- self . a_cur = self . a . next ( ) ;
354
+ * a_cur = Some ( a. next ( ) ) ;
349
355
x
350
356
}
351
357
}
352
358
}
353
359
Some ( x) => x,
354
360
} ;
355
- self . a_cur . as_ref ( ) . map ( |a| ( a. clone ( ) , elt_b) )
361
+ a_cur
362
+ . get_or_insert_with ( || a. next ( ) )
363
+ . as_ref ( )
364
+ . map ( |a| ( a. clone ( ) , elt_b) )
356
365
}
357
366
358
367
fn size_hint ( & self ) -> ( usize , Option < usize > ) {
359
- let has_cur = self . a_cur . is_some ( ) as usize ;
368
+ let has_cur = matches ! ( self . a_cur, Some ( Some ( _ ) ) ) as usize ;
360
369
// Not ExactSizeIterator because size may be larger than usize
361
370
let ( b_min, b_max) = self . b . size_hint ( ) ;
362
371
@@ -367,21 +376,26 @@ where
367
376
)
368
377
}
369
378
370
- fn fold < Acc , G > ( mut self , mut accum : Acc , mut f : G ) -> Acc
379
+ fn fold < Acc , G > ( self , mut accum : Acc , mut f : G ) -> Acc
371
380
where
372
381
G : FnMut ( Acc , Self :: Item ) -> Acc ,
373
382
{
374
383
// use a split loop to handle the loose a_cur as well as avoiding to
375
384
// clone b_orig at the end.
376
- if let Some ( mut a) = self . a_cur . take ( ) {
377
- let mut b = self . b ;
385
+ let Self {
386
+ mut a,
387
+ a_cur,
388
+ mut b,
389
+ b_orig,
390
+ } = self ;
391
+ if let Some ( mut elt_a) = a_cur. unwrap_or_else ( || a. next ( ) ) {
378
392
loop {
379
- accum = b. fold ( accum, |acc, elt| f ( acc, ( a . clone ( ) , elt) ) ) ;
393
+ accum = b. fold ( accum, |acc, elt| f ( acc, ( elt_a . clone ( ) , elt) ) ) ;
380
394
381
395
// we can only continue iterating a if we had a first element;
382
- if let Some ( next_a ) = self . a . next ( ) {
383
- b = self . b_orig . clone ( ) ;
384
- a = next_a ;
396
+ if let Some ( next_elt_a ) = a. next ( ) {
397
+ b = b_orig. clone ( ) ;
398
+ elt_a = next_elt_a ;
385
399
} else {
386
400
break ;
387
401
}
0 commit comments