ソースを参照

Implement sticy promotions

Billy Barrow 1 ヶ月 前
コミット
7f322cfaa0

+ 3 - 3
src/lib/Promotions/EquatableEnumerable.vala

@@ -1,12 +1,12 @@
 namespace Invercargill {
 
-    public class Equatables<T> : ProxyEnumerable<T>, Promotion<T>, Equatable<Enumerable<T>> {
+    public class Equatables<T> : StickyPromotion<T, Equatables<T>>, Promotion<T>, Equatable<Enumerable<T>> {
 
-        public bool can_wrap(GLib.Type element_type) {
+        public override bool can_wrap(GLib.Type element_type) {
             return element_type.is_a(typeof(Equatable));
         }
 
-        public Enumerable<T> wrap (Enumerable<T> enumerable) {
+        public override Enumerable<T> wrap (Enumerable<T> enumerable) {
             inner = enumerable;
             return this;
         }

+ 12 - 12
src/lib/Promotions/Numbers/Implementations.vala

@@ -1,6 +1,6 @@
 namespace Invercargill {
 
-    public class SignedNativeIntegers : NumberEnumerable<int> {
+    public class SignedNativeIntegers : NumberEnumerable<int, SignedNativeIntegers> {
         public override bool can_wrap(GLib.Type element_type) {
             return element_type.is_a(typeof(int));
         }
@@ -33,7 +33,7 @@ namespace Invercargill {
         }        
     }
 
-    public class UnsignedNativeIntegers : NumberEnumerable<uint> {
+    public class UnsignedNativeIntegers : NumberEnumerable<uint, UnsignedNativeIntegers> {
         public override bool can_wrap(GLib.Type element_type) {
             return element_type.is_a(typeof(uint));
         }
@@ -66,7 +66,7 @@ namespace Invercargill {
         }      
     }
 
-    public class Signed8BitIntegers : NumberEnumerable<int8> {
+    public class Signed8BitIntegers : NumberEnumerable<int8, Signed8BitIntegers> {
         public override bool can_wrap(GLib.Type element_type) {
             return element_type.is_a(typeof(int8));
         }
@@ -99,7 +99,7 @@ namespace Invercargill {
         }      
     }
 
-    public class Unsigned8BitIntegers : NumberEnumerable<uint8> {
+    public class Unsigned8BitIntegers : NumberEnumerable<uint8, Unsigned8BitIntegers> {
         public override bool can_wrap(GLib.Type element_type) {
             return element_type.is_a(typeof(uint8));
         }
@@ -132,7 +132,7 @@ namespace Invercargill {
         }      
     }
 
-    public class Signed16BitIntegers : NumberEnumerable<int16> {
+    public class Signed16BitIntegers : NumberEnumerable<int16, Signed16BitIntegers> {
         public override bool can_wrap(GLib.Type element_type) {
             return element_type.is_a(typeof(int16));
         }
@@ -165,7 +165,7 @@ namespace Invercargill {
         }      
     }
 
-    public class Unsigned16BitIntegers : NumberEnumerable<uint16> {
+    public class Unsigned16BitIntegers : NumberEnumerable<uint16, Unsigned16BitIntegers> {
         public override bool can_wrap(GLib.Type element_type) {
             return element_type.is_a(typeof(uint16));
         }
@@ -198,7 +198,7 @@ namespace Invercargill {
         }      
     }
 
-    public class Signed32BitIntegers : NumberEnumerable<int32> {
+    public class Signed32BitIntegers : NumberEnumerable<int32, Signed32BitIntegers> {
         public override bool can_wrap(GLib.Type element_type) {
             return element_type.is_a(typeof(int32));
         }
@@ -231,7 +231,7 @@ namespace Invercargill {
         }      
     }
 
-    public class Unsigned32BitIntegers : NumberEnumerable<uint32> {
+    public class Unsigned32BitIntegers : NumberEnumerable<uint32, Unsigned32BitIntegers> {
         public override bool can_wrap(GLib.Type element_type) {
             return element_type.is_a(typeof(uint32));
         }
@@ -264,7 +264,7 @@ namespace Invercargill {
         }      
     }
 
-    public class Signed64BitIntegers : NumberEnumerable<int64?> {
+    public class Signed64BitIntegers : NumberEnumerable<int64?, Signed64BitIntegers> {
         public override bool can_wrap(GLib.Type element_type) {
             return element_type.is_a(typeof(int64?));
         }
@@ -297,7 +297,7 @@ namespace Invercargill {
         }      
     }
 
-    public class Unsigned64BitIntegers : NumberEnumerable<uint64?> {
+    public class Unsigned64BitIntegers : NumberEnumerable<uint64?, Unsigned64BitIntegers> {
         public override bool can_wrap(GLib.Type element_type) {
             return element_type.is_a(typeof(uint64?));
         }
@@ -330,7 +330,7 @@ namespace Invercargill {
         }      
     }
 
-    public class Doubles : NumberEnumerable<double?> {
+    public class Doubles : NumberEnumerable<double?, Doubles> {
         public override bool can_wrap(GLib.Type element_type) {
             return element_type.is_a(typeof(double?));
         }
@@ -363,7 +363,7 @@ namespace Invercargill {
         }      
     }
 
-    public class Floats : NumberEnumerable<float?> {
+    public class Floats : NumberEnumerable<float?, Floats> {
         public override bool can_wrap(GLib.Type element_type) {
             return element_type.is_a(typeof(float?));
         }

+ 2 - 3
src/lib/Promotions/Numbers/NumberEnumerable.vala

@@ -1,7 +1,6 @@
 namespace Invercargill {
 
-    public abstract class NumberEnumerable<T> : ProxyEnumerable<T>, Promotion<T>, Equatable<Enumerable<T>> {
-        public abstract bool can_wrap (GLib.Type element_type);
+    public abstract class NumberEnumerable<T, TSelf> : StickyPromotion<T, TSelf>, Promotion<T>, Equatable<Enumerable<T>> {
 
         protected abstract bool greater_than(T a, T b);
         protected abstract bool less_than(T a, T b);
@@ -66,7 +65,7 @@ namespace Invercargill {
             return value;
         }
 
-        public Enumerable<T> wrap (Enumerable<T> enumerable) {
+        public override Enumerable<T> wrap (Enumerable<T> enumerable) {
             inner = enumerable;
             return this;
         }

+ 3 - 3
src/lib/Promotions/PropertyGroupEnumerable.vala

@@ -1,13 +1,13 @@
 namespace Invercargill {
 
-    public class PropertyGroups : ProxyEnumerable<Properties>, Promotion<Properties> {
+    public class PropertyGroups : StickyPromotion<Properties, PropertyGroups>, Promotion<Properties> {
 
-        public Enumerable<Properties> wrap (Enumerable<Properties> enumerable) {
+        public override Enumerable<Properties> wrap (Enumerable<Properties> enumerable) {
             inner = enumerable;
             return this;
         }
 
-        public bool can_wrap (GLib.Type element_type) {
+        public override bool can_wrap (GLib.Type element_type) {
             return element_type.is_a (typeof(Properties));
         }
 

+ 41 - 0
src/lib/StickyPromotion.vala

@@ -0,0 +1,41 @@
+namespace Invercargill {
+
+    public abstract class StickyPromotion<T, TPromotion> : ProxyEnumerable<T>, Promotion<T> {
+
+        public abstract Enumerable<T> wrap(Enumerable<T> enumerable);
+        public abstract bool can_wrap(GLib.Type element_type);
+
+        public new TPromotion where(owned PredicateDelegate<T> predicate) {
+            return (TPromotion)wrap(inner.where((owned)predicate));
+        }
+    
+        public new TPromotion sort(owned CompareDelegate<T> compare) {
+            return (TPromotion)wrap(inner.sort((owned)compare));
+        }
+    
+        public new TPromotion concat(Enumerable<T> other) {
+            return (TPromotion)wrap(inner.concat(other));
+        }
+    
+        public new TPromotion take(int count) {
+            return (TPromotion)wrap(inner.take(count));
+        }
+    
+        public new TPromotion skip(int count) {
+            return (TPromotion)wrap(inner.skip(count));
+        }
+    
+        public new TPromotion with(T item) {
+            return (TPromotion)wrap(inner.with(item));
+        }
+    
+        public new TPromotion seal() {
+            return (TPromotion)wrap(inner.seal());
+        }
+
+        public new TPromotion cache() {
+            return (TPromotion)wrap(inner.cache());
+        }
+    }
+
+}

+ 1 - 0
src/lib/meson.build

@@ -28,6 +28,7 @@ sources += files('KeyValuePair.vala')
 sources += files('Attempt.vala')
 sources += files('Cache.vala')
 sources += files('EnumerableProxy.vala')
+sources += files('StickyPromotion.vala')
 
 sources += files('Modifiers/Query.vala')
 sources += files('Modifiers/Transform.vala')

+ 14 - 0
src/tests/Integration/Promotion.vala

@@ -23,4 +23,18 @@ void promotion_tests() {
         
         assert_true(data == new_data);
     });
+
+    Test.add_func("/invercargill/promotions/sticky", () => { 
+        try {
+            var sum = range(0, 10000, 1)
+                .promote_to<Signed32BitIntegers>()
+                .where(i => i % 2 != 0)
+                .sum();
+
+            assert_cmpint(sum, CompareOperator.EQ, 25000000);
+        }
+        catch (Error e) {
+            assert_no_error(e);
+        }
+    });
 }