123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194 |
- namespace Invercargill {
- public abstract class Enumerable<T> {
- public abstract Tracker<T> get_tracker();
- // Returns false if iteration was interrupted
- // Returns true if iteration reached natural end
- public virtual bool iterate_if(PredicateDelegate<T> handler) {
- var tracker = get_tracker();
- while(tracker.has_next()) {
- if(!handler(tracker.get_next())) {
- return false;
- }
- }
- return true;
- }
- public virtual void iterate(ItemDelegate<T> handler) {
- iterate_if(i => {
- handler(i);
- return true;
- });
- }
- public virtual Sequence<T> to_sequence() {
- var sequence = new Sequence<T>();
- iterate(i => sequence.add(i));
- return sequence;
- }
- public virtual Gee.Collection<T> to_collection() {
- var collection = new Gee.LinkedList<T>();
- iterate(i => collection.add(i));
- return collection;
- }
- public virtual Gee.Iterable<T> as_iterable() {
- return new GeeIterable<T>(this);
- }
- public virtual T[] to_array() {
- return to_collection().to_array();
- }
- public virtual int count() {
- var count = 0;
- iterate(i => count++);
- return count;
- }
- public virtual bool any(PredicateDelegate<T> predicate) {
- var result = false;
- iterate_if(i => {
- if(predicate(i)) {
- result = true;
- return false;
- }
- return true;
- });
- return result;
- }
- public virtual bool all(PredicateDelegate<T> predicate) {
- return !any(i => !predicate(i));
- }
- public virtual bool no(PredicateDelegate<T> predicate) {
- return all(i => !predicate(i));
- }
- public virtual Enumerable<T> where(owned PredicateDelegate<T> predicate) {
- return new FilterQuery<T>(this, (owned)predicate);
- }
- public virtual Enumerable<Tout> select<Tout>(owned TransformDelegate<T, Tout> transform) {
- return new TransformQuery<T, Tout>(this, (owned)transform);
- }
- public virtual Enumerable<Tout> select_many<Tout>(owned TransformDelegate<T, Enumerable<Tout>> transform) {
- return new MergeQuery<Tout>(select((owned)transform));
- }
- public virtual Enumerable<T> sort(owned CompareDelegate<T> compare) {
- return new SortQuery<T>(this, (owned)compare);
- }
- public virtual Enumerable<T> concat(Enumerable<T> other) {
- return new ConcatEnumerable<T>(this, other);
- }
- public virtual Enumerable<T> take(int count) {
- return new TakeQuery<T>(this, count);
- }
- public virtual Enumerable<T> skip(int count) {
- return new SkipQuery<T>(this, count);
- }
- public virtual Tout aggrigate<Tout>(Tout initial, AggrigateDelegate<Tout, T> aggrigate_func) {
- var aggrigate = initial;
- iterate(i => {
- aggrigate = aggrigate_func(aggrigate, i);
- });
- return aggrigate;
- }
- public virtual bool contains(T item) {
- return any(i => i == item);
- }
- public virtual Enumerable<Pair<T, Tother>> pair<Tother>(Enumerable<Tother> other) {
- return new PairEnumerable<T, Tother>(this, other);
- }
- public virtual Enumerable<T> zip(Enumerable<T> other) {
- return new ZipperEnumerable<T>(this, other);
- }
- public virtual Enumerable<Tout> fork<Tout>(owned TransformDelegate<T, Tout> fork1, owned TransformDelegate<T, Tout> fork2) {
- var seq = to_sequence();
- return seq.select<Tout>((owned)fork1).zip(seq.select<Tout>((owned)fork2));
- }
- public virtual Enumerable<Tout> fork_many<Tout>(owned TransformDelegate<T, Enumerable<Tout>> fork1, owned TransformDelegate<T, Enumerable<Tout>> fork2) {
- return new MergeQuery<Tout>(fork((owned)fork1, (owned)fork2));
- }
- public virtual bool matches(Enumerable<T> other, EqualityDelegate<T> equals) {
- return pair(other).all(p => equals(p.value1, p.value2));
- }
- public virtual Enumerable<T> with(T item) {
- var seq = new Sequence<T>();
- seq.add(item);
- return concat(seq);
- }
- public virtual T first() throws SequenceError {
- var tracker = get_tracker();
- if(tracker.has_next()) {
- return tracker.get_next();
- }
- throw new SequenceError.NO_ELEMENTS("The sequence contains no elements");
- }
- public virtual T? first_or_default() {
- var tracker = get_tracker();
- if(tracker.has_next()) {
- return tracker.get_next();
- }
- return null;
- }
- public virtual T single() throws SequenceError {
- var tracker = get_tracker();
- if(tracker.has_next()) {
- var item = tracker.get_next();
- if(tracker.has_next()) {
- throw new SequenceError.MULTUPLE_ELEMENTS("The sequence contains more than one element");
- }
- return item;
- }
- throw new SequenceError.NO_ELEMENTS("The sequence contains no elements");
- }
- public virtual T single_or_default() throws SequenceError {
- var tracker = get_tracker();
- if(tracker.has_next()) {
- var item = tracker.get_next();
- if(tracker.has_next()) {
- throw new SequenceError.MULTUPLE_ELEMENTS("The sequence contains more than one element");
- }
- return item;
- }
- return null;
- }
- public virtual string to_string(TransformDelegate<T, string> stringifier, string seperator = "") {
- bool is_first = false;
- return aggrigate<string>("", (s, v) => {
- if(is_first) {
- is_first = true;
- return stringifier(v);
- }
- return s + seperator + stringifier(v);
- });
- }
- }
- }
|