OLD | NEW |
1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 part of dart._internal; | 5 part of dart._internal; |
6 | 6 |
7 /** | 7 /** |
8 * Marker interface for [Iterable] subclasses that have an efficient | 8 * Marker interface for [Iterable] subclasses that have an efficient |
9 * [length] implementation. | 9 * [length] implementation. |
10 */ | 10 */ |
(...skipping 339 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
350 final Iterable<S> _iterable; | 350 final Iterable<S> _iterable; |
351 final _Transformation<S, T> _f; | 351 final _Transformation<S, T> _f; |
352 | 352 |
353 factory MappedIterable(Iterable<S> iterable, T function(S value)) { | 353 factory MappedIterable(Iterable<S> iterable, T function(S value)) { |
354 if (iterable is EfficientLengthIterable) { | 354 if (iterable is EfficientLengthIterable) { |
355 return new EfficientLengthMappedIterable<S, T>(iterable, function); | 355 return new EfficientLengthMappedIterable<S, T>(iterable, function); |
356 } | 356 } |
357 return new MappedIterable<S, T>._(iterable, function); | 357 return new MappedIterable<S, T>._(iterable, function); |
358 } | 358 } |
359 | 359 |
360 MappedIterable._(this._iterable, T this._f(S element)); | 360 MappedIterable._(this._iterable, this._f); |
361 | 361 |
362 Iterator<T> get iterator => new MappedIterator<S, T>(_iterable.iterator, _f); | 362 Iterator<T> get iterator => new MappedIterator<S, T>(_iterable.iterator, _f); |
363 | 363 |
364 // Length related functions are independent of the mapping. | 364 // Length related functions are independent of the mapping. |
365 int get length => _iterable.length; | 365 int get length => _iterable.length; |
366 bool get isEmpty => _iterable.isEmpty; | 366 bool get isEmpty => _iterable.isEmpty; |
367 | 367 |
368 // Index based lookup can be done before transforming. | 368 // Index based lookup can be done before transforming. |
369 T get first => _f(_iterable.first); | 369 T get first => _f(_iterable.first); |
370 T get last => _f(_iterable.last); | 370 T get last => _f(_iterable.last); |
371 T get single => _f(_iterable.single); | 371 T get single => _f(_iterable.single); |
372 T elementAt(int index) => _f(_iterable.elementAt(index)); | 372 T elementAt(int index) => _f(_iterable.elementAt(index)); |
373 } | 373 } |
374 | 374 |
375 class EfficientLengthMappedIterable<S, T> extends MappedIterable<S, T> | 375 class EfficientLengthMappedIterable<S, T> extends MappedIterable<S, T> |
376 implements EfficientLengthIterable<T> { | 376 implements EfficientLengthIterable<T> { |
377 EfficientLengthMappedIterable(Iterable<S> iterable, T function(S value)) | 377 EfficientLengthMappedIterable(Iterable<S> iterable, T function(S value)) |
378 : super._(iterable, function); | 378 : super._(iterable, function); |
379 } | 379 } |
380 | 380 |
381 class MappedIterator<S, T> extends Iterator<T> { | 381 class MappedIterator<S, T> extends Iterator<T> { |
382 T _current; | 382 T _current; |
383 final Iterator<S> _iterator; | 383 final Iterator<S> _iterator; |
384 final _Transformation<S, T> _f; | 384 final _Transformation<S, T> _f; |
385 | 385 |
386 MappedIterator(this._iterator, T this._f(S element)); | 386 MappedIterator(this._iterator, this._f); |
387 | 387 |
388 bool moveNext() { | 388 bool moveNext() { |
389 if (_iterator.moveNext()) { | 389 if (_iterator.moveNext()) { |
390 _current = _f(_iterator.current); | 390 _current = _f(_iterator.current); |
391 return true; | 391 return true; |
392 } | 392 } |
393 _current = null; | 393 _current = null; |
394 return false; | 394 return false; |
395 } | 395 } |
396 | 396 |
397 T get current => _current; | 397 T get current => _current; |
398 } | 398 } |
399 | 399 |
400 /** | 400 /** |
401 * Specialized alternative to [MappedIterable] for mapped [List]s. | 401 * Specialized alternative to [MappedIterable] for mapped [List]s. |
402 * | 402 * |
403 * Expects efficient `length` and `elementAt` on the source iterable. | 403 * Expects efficient `length` and `elementAt` on the source iterable. |
404 */ | 404 */ |
405 class MappedListIterable<S, T> extends ListIterable<T> { | 405 class MappedListIterable<S, T> extends ListIterable<T> { |
406 final Iterable<S> _source; | 406 final Iterable<S> _source; |
407 final _Transformation<S, T> _f; | 407 final _Transformation<S, T> _f; |
408 | 408 |
409 MappedListIterable(this._source, T this._f(S value)); | 409 MappedListIterable(this._source, this._f); |
410 | 410 |
411 int get length => _source.length; | 411 int get length => _source.length; |
412 T elementAt(int index) => _f(_source.elementAt(index)); | 412 T elementAt(int index) => _f(_source.elementAt(index)); |
413 } | 413 } |
414 | 414 |
415 | 415 |
416 typedef bool _ElementPredicate<E>(E element); | 416 typedef bool _ElementPredicate<E>(E element); |
417 | 417 |
418 class WhereIterable<E> extends Iterable<E> { | 418 class WhereIterable<E> extends Iterable<E> { |
419 final Iterable<E> _iterable; | 419 final Iterable<E> _iterable; |
420 final _ElementPredicate<E> _f; | 420 final _ElementPredicate<E> _f; |
421 | 421 |
422 WhereIterable(this._iterable, bool this._f(E element)); | 422 WhereIterable(this._iterable, this._f); |
423 | 423 |
424 Iterator<E> get iterator => new WhereIterator<E>(_iterable.iterator, _f); | 424 Iterator<E> get iterator => new WhereIterator<E>(_iterable.iterator, _f); |
425 | 425 |
426 // Specialization of [Iterable.map] to non-EfficientLengthIterable. | 426 // Specialization of [Iterable.map] to non-EfficientLengthIterable. |
427 Iterable<T> map<T>(T f(E element)) => new MappedIterable<E, T>._(this, f); | 427 Iterable<T> map<T>(T f(E element)) => new MappedIterable<E, T>._(this, f); |
428 } | 428 } |
429 | 429 |
430 class WhereIterator<E> extends Iterator<E> { | 430 class WhereIterator<E> extends Iterator<E> { |
431 final Iterator<E> _iterator; | 431 final Iterator<E> _iterator; |
432 final _ElementPredicate _f; | 432 final _ElementPredicate _f; |
433 | 433 |
434 WhereIterator(this._iterator, bool this._f(E element)); | 434 WhereIterator(this._iterator, this._f); |
435 | 435 |
436 bool moveNext() { | 436 bool moveNext() { |
437 while (_iterator.moveNext()) { | 437 while (_iterator.moveNext()) { |
438 if (_f(_iterator.current)) { | 438 if (_f(_iterator.current)) { |
439 return true; | 439 return true; |
440 } | 440 } |
441 } | 441 } |
442 return false; | 442 return false; |
443 } | 443 } |
444 | 444 |
445 E get current => _iterator.current; | 445 E get current => _iterator.current; |
446 } | 446 } |
447 | 447 |
448 typedef Iterable<T> _ExpandFunction<S, T>(S sourceElement); | 448 typedef Iterable<T> _ExpandFunction<S, T>(S sourceElement); |
449 | 449 |
450 class ExpandIterable<S, T> extends Iterable<T> { | 450 class ExpandIterable<S, T> extends Iterable<T> { |
451 final Iterable<S> _iterable; | 451 final Iterable<S> _iterable; |
452 final _ExpandFunction<S, T> _f; | 452 final _ExpandFunction<S, T> _f; |
453 | 453 |
454 ExpandIterable(this._iterable, Iterable<T> this._f(S element)); | 454 ExpandIterable(this._iterable, this._f); |
455 | 455 |
456 Iterator<T> get iterator => new ExpandIterator<S, T>(_iterable.iterator, _f); | 456 Iterator<T> get iterator => new ExpandIterator<S, T>(_iterable.iterator, _f); |
457 } | 457 } |
458 | 458 |
459 class ExpandIterator<S, T> implements Iterator<T> { | 459 class ExpandIterator<S, T> implements Iterator<T> { |
460 final Iterator<S> _iterator; | 460 final Iterator<S> _iterator; |
461 final _ExpandFunction<S, T> _f; | 461 final _ExpandFunction<S, T> _f; |
462 // Initialize _currentExpansion to an empty iterable. A null value | 462 // Initialize _currentExpansion to an empty iterable. A null value |
463 // marks the end of iteration, and we don't want to call _f before | 463 // marks the end of iteration, and we don't want to call _f before |
464 // the first moveNext call. | 464 // the first moveNext call. |
465 Iterator<T> _currentExpansion = const EmptyIterator(); | 465 Iterator<T> _currentExpansion = const EmptyIterator(); |
466 T _current; | 466 T _current; |
467 | 467 |
468 ExpandIterator(this._iterator, Iterable<T> this._f(S element)); | 468 ExpandIterator(this._iterator, this._f); |
469 | 469 |
470 T get current => _current; | 470 T get current => _current; |
471 | 471 |
472 bool moveNext() { | 472 bool moveNext() { |
473 if (_currentExpansion == null) return false; | 473 if (_currentExpansion == null) return false; |
474 while (!_currentExpansion.moveNext()) { | 474 while (!_currentExpansion.moveNext()) { |
475 _current = null; | 475 _current = null; |
476 if (_iterator.moveNext()) { | 476 if (_iterator.moveNext()) { |
477 // If _f throws, this ends iteration. Otherwise _currentExpansion and | 477 // If _f throws, this ends iteration. Otherwise _currentExpansion and |
478 // _current will be set again below. | 478 // _current will be set again below. |
(...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
541 E get current { | 541 E get current { |
542 if (_remaining < 0) return null; | 542 if (_remaining < 0) return null; |
543 return _iterator.current; | 543 return _iterator.current; |
544 } | 544 } |
545 } | 545 } |
546 | 546 |
547 class TakeWhileIterable<E> extends Iterable<E> { | 547 class TakeWhileIterable<E> extends Iterable<E> { |
548 final Iterable<E> _iterable; | 548 final Iterable<E> _iterable; |
549 final _ElementPredicate<E> _f; | 549 final _ElementPredicate<E> _f; |
550 | 550 |
551 TakeWhileIterable(this._iterable, bool this._f(E element)); | 551 TakeWhileIterable(this._iterable, this._f); |
552 | 552 |
553 Iterator<E> get iterator { | 553 Iterator<E> get iterator { |
554 return new TakeWhileIterator<E>(_iterable.iterator, _f); | 554 return new TakeWhileIterator<E>(_iterable.iterator, _f); |
555 } | 555 } |
556 } | 556 } |
557 | 557 |
558 class TakeWhileIterator<E> extends Iterator<E> { | 558 class TakeWhileIterator<E> extends Iterator<E> { |
559 final Iterator<E> _iterator; | 559 final Iterator<E> _iterator; |
560 final _ElementPredicate<E> _f; | 560 final _ElementPredicate<E> _f; |
561 bool _isFinished = false; | 561 bool _isFinished = false; |
562 | 562 |
563 TakeWhileIterator(this._iterator, bool this._f(E element)); | 563 TakeWhileIterator(this._iterator, this._f); |
564 | 564 |
565 bool moveNext() { | 565 bool moveNext() { |
566 if (_isFinished) return false; | 566 if (_isFinished) return false; |
567 if (!_iterator.moveNext() || !_f(_iterator.current)) { | 567 if (!_iterator.moveNext() || !_f(_iterator.current)) { |
568 _isFinished = true; | 568 _isFinished = true; |
569 return false; | 569 return false; |
570 } | 570 } |
571 return true; | 571 return true; |
572 } | 572 } |
573 | 573 |
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
634 return _iterator.moveNext(); | 634 return _iterator.moveNext(); |
635 } | 635 } |
636 | 636 |
637 E get current => _iterator.current; | 637 E get current => _iterator.current; |
638 } | 638 } |
639 | 639 |
640 class SkipWhileIterable<E> extends Iterable<E> { | 640 class SkipWhileIterable<E> extends Iterable<E> { |
641 final Iterable<E> _iterable; | 641 final Iterable<E> _iterable; |
642 final _ElementPredicate<E> _f; | 642 final _ElementPredicate<E> _f; |
643 | 643 |
644 SkipWhileIterable(this._iterable, bool this._f(E element)); | 644 SkipWhileIterable(this._iterable, this._f); |
645 | 645 |
646 Iterator<E> get iterator { | 646 Iterator<E> get iterator { |
647 return new SkipWhileIterator<E>(_iterable.iterator, _f); | 647 return new SkipWhileIterator<E>(_iterable.iterator, _f); |
648 } | 648 } |
649 } | 649 } |
650 | 650 |
651 class SkipWhileIterator<E> extends Iterator<E> { | 651 class SkipWhileIterator<E> extends Iterator<E> { |
652 final Iterator<E> _iterator; | 652 final Iterator<E> _iterator; |
653 final _ElementPredicate<E> _f; | 653 final _ElementPredicate<E> _f; |
654 bool _hasSkipped = false; | 654 bool _hasSkipped = false; |
655 | 655 |
656 SkipWhileIterator(this._iterator, bool this._f(E element)); | 656 SkipWhileIterator(this._iterator, this._f); |
657 | 657 |
658 bool moveNext() { | 658 bool moveNext() { |
659 if (!_hasSkipped) { | 659 if (!_hasSkipped) { |
660 _hasSkipped = true; | 660 _hasSkipped = true; |
661 while (_iterator.moveNext()) { | 661 while (_iterator.moveNext()) { |
662 if (!_f(_iterator.current)) return true; | 662 if (!_f(_iterator.current)) return true; |
663 } | 663 } |
664 } | 664 } |
665 return _iterator.moveNext(); | 665 return _iterator.moveNext(); |
666 } | 666 } |
(...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
755 * Creates errors throw by [Iterable] when the element count is wrong. | 755 * Creates errors throw by [Iterable] when the element count is wrong. |
756 */ | 756 */ |
757 abstract class IterableElementError { | 757 abstract class IterableElementError { |
758 /** Error thrown thrown by, e.g., [Iterable.first] when there is no result. */ | 758 /** Error thrown thrown by, e.g., [Iterable.first] when there is no result. */ |
759 static StateError noElement() => new StateError("No element"); | 759 static StateError noElement() => new StateError("No element"); |
760 /** Error thrown by, e.g., [Iterable.single] if there are too many results. */ | 760 /** Error thrown by, e.g., [Iterable.single] if there are too many results. */ |
761 static StateError tooMany() => new StateError("Too many elements"); | 761 static StateError tooMany() => new StateError("Too many elements"); |
762 /** Error thrown by, e.g., [List.setRange] if there are too few elements. */ | 762 /** Error thrown by, e.g., [List.setRange] if there are too few elements. */ |
763 static StateError tooFew() => new StateError("Too few elements"); | 763 static StateError tooFew() => new StateError("Too few elements"); |
764 } | 764 } |
OLD | NEW |