Ranides Atterwim %!s(int64=4) %!d(string=hai) anos
pai
achega
861ef09a0d

+ 2 - 2
assira.core/src/main/java/net/ranides/assira/collection/query/base/CQArray.java

@@ -109,8 +109,8 @@ public class CQArray<T> extends CQueryAbstract<T> {
 
     @Override
     public CQuery<T> slice(int begin, int end) {
-        int b = MathUtils.add(0, this.end, this.begin, begin);
-        int e = MathUtils.add(b, this.end, this.begin, end);
+        int b = MathUtils.adds(this.begin, begin, 0, this.end);
+        int e = MathUtils.adds(this.begin, end, b, this.end);
         return new CQArray<>(data, b, e);
     }
 

+ 2 - 2
assira.core/src/main/java/net/ranides/assira/collection/query/derived/CQSlice.java

@@ -87,8 +87,8 @@ public class CQSlice<T> extends CQueryAbstract<T> {
 
     @Override
     public CQuery<T> slice(int begin, int end) {
-        int b = MathUtils.add(0, this.end, this.begin, begin);
-        int e = MathUtils.add(b, this.end, this.begin, end);
+        int b = MathUtils.adds(this.begin, begin, 0, this.end);
+        int e = MathUtils.adds(this.begin, end, b, this.end);
         return new CQSlice<>(source, b, e);
     }
 

+ 26 - 4
assira.core/src/main/java/net/ranides/assira/math/MathUtils.java

@@ -226,7 +226,7 @@ public final class MathUtils {
      * @param y y
      * @return x+y
      */
-    public static int add(int x, int y) {
+    public static int adds(int x, int y) {
         int r = x + y;
         if (((r ^ x) & (r ^ y)) < 0) {
             return Integer.MIN_VALUE - (r >>> 31);
@@ -234,8 +234,17 @@ public final class MathUtils {
         return r;
     }
 
-    public static int add(int min, int max, int x, int y) {
-        return (int)clip((long)x + (long)y, min, max);
+    /**
+     * Saturated add. Returns min or max instead of overflow.
+     *
+     * @param x
+     * @param y
+     * @param min
+     * @param max
+     * @return
+     */
+    public static int adds(int x, int y, int min, int max) {
+        return clip(adds(x,y), min, max);
     }
 
     /**
@@ -245,12 +254,25 @@ public final class MathUtils {
      * @param y y
      * @return x+y
      */
-    public static long add(long x, long y) {
+    public static long adds(long x, long y) {
         long r = x + y;
         if (((r ^ x) & (r ^ y)) < 0) {
             return Long.MIN_VALUE - (r >>> 63);
         }
         return r;
     }
+
+    /**
+     * Saturated add. Returns min or max instead of overflow.
+     *
+     * @param x
+     * @param y
+     * @param min
+     * @param max
+     * @return
+     */
+    public static long adds(long x, long y, long min, long max) {
+        return clip(adds(x,y), min, max);
+    }
 }
 

+ 24 - 11
assira.core/src/test/java/net/ranides/assira/collection/query/CQueryFunctionTest.java

@@ -60,20 +60,33 @@ public class CQueryFunctionTest {
     }
 
     @Test
-    public void complexFilter() {
-        //              0 ... 100
-        // skip(5)      5 ... 100
-        // filter(v -> v%3 !=0)     5,7,8,10,11,13,14,16,18, ... 97,98,100
-        // slice(7,) 16 ... 89
-        CQueryFunction<Integer, Integer> func = CQueryFunction.<Integer>prepare()
+    public void skipFilterSlice() {
+        CQueryFunction<Integer, Integer> func1 = CQueryFunction.<Integer>prepare()
+            // 5 .. 49
             .skip(5)
+            // 5,7,8,10,11,13,14,16,18, ... 41,43,44,46,47,49
             .filter(v -> v % 3 != 0)
-            .slice(7, 47);
+            // 16 ... 89
+            .slice(7, 22);
+
+        List<Integer> exp1 = Arrays.asList(16, 17, 19, 20, 22, 23, 25, 26, 28, 29, 31, 32, 34, 35, 37);
+
+        CQueryAssert.assertEquals(exp1, CQuery.from().range(0, 50).apply(func1));
+
+        CQueryFunction<Integer, Integer> func2 = CQueryFunction.<Integer>prepare()
+            // 0 .. 24
+            .limit(v -> v < 25)
+            // 100 .. 124
+            .map(v -> 100 + v)
+            // 106 .. 119
+            .filterEach((i,v) -> i>5 && i<20)
+            // 107,109,111 .. 119
+            .discard(v -> v%2 ==0)
+            .sort(IntComparator.DESC);
 
-        List<Integer> exp = Arrays.asList(16, 17, 19, 20, 22, 23, 25, 26, 28, 29, 31, 32, 34, 35, 37, 38, 40, 41, 43, 44, 46, 47, 49, 50, 52, 53, 55, 56, 58, 59, 61, 62, 64, 65, 67, 68, 70, 71, 73, 74);
-        CQuery<Integer> query = CQuery.from().range(0, 100).apply(func);
-        
-        CQueryAssert.assertEquals(exp, query);
+        List<Integer> exp2 = Arrays.asList(119, 117, 115, 113, 111, 109, 107);
+        CQueryAssert.assertEquals(exp2, CQuery.from().range(0, 50).apply(func2));
     }
 
+
 }

+ 27 - 31
assira.core/src/test/java/net/ranides/assira/collection/query/base/CQArrayTest.java

@@ -5,7 +5,9 @@ import org.junit.Test;
 
 import net.ranides.assira.collection.query.CQuery;
 
+import java.util.ArrayList;
 import java.util.Arrays;
+import java.util.List;
 
 import static org.junit.Assert.*;
 
@@ -22,37 +24,31 @@ public class CQArrayTest {
         CQueryAssert.assertEquals(Arrays.asList(2,3), CQuery.from().values(input).limit(4).slice(2,4));
         CQueryAssert.assertEquals(Arrays.asList(2,3), CQuery.from().values(input).limit(4).slice(2,6));
 
-//        List<Integer> out3 = new ArrayList<>();
-//        assertEquals(18, CQuery.from().values(input).skip(2).limit(4).onEach(v -> out3.add(v)).reduce(Integer::sum).intValue());
-//        assertEquals(Arrays.asList(2,3,4,9), out3);
-
-
-
-
-//        List<String> out4 = new ArrayList<>();
-//        assertEquals(64, CQuery.from().values(input)
-//            .onEach((i,v) -> out4.add(i+"#"+v))
-//            .reduce(Integer::sum).intValue()
-//        );
-//        assertEquals(Arrays.asList("0#7", "1#6", "2#2", "3#3", "4#4", "5#9", "6#2", "7#5", "8#1", "9#6", "10#7", "11#8", "12#4"), out4);
-//
-//
-//        List<String> out5 = new ArrayList<>();
-//        assertEquals(18, CQuery.from().values(input)
-//            .limit(4).onEach((i, v) -> out5.add(i + "#" + v))
-//            .reduce(Integer::sum).intValue()
-//        );
-//        assertEquals(Arrays.asList("0#7", "1#6", "2#2", "3#3"), out5);
-//
-//        List<String> out6 = new ArrayList<>();
-//        assertEquals(18, CQuery.from().values(input)
-//            .onEach((i, v) -> out6.add(i + "#" + v)).limit(4)
-//            .reduce(Integer::sum).intValue()
-//        );
-//
-//        assertEquals(Arrays.asList("0#7", "1#6", "2#2", "3#3"), out6);
-
-        // TODO #onEach for slices (begin,end)
+        List<Integer> out3 = new ArrayList<>();
+        assertEquals(18, CQuery.from().values(input).skip(2).limit(4).onEach(v -> out3.add(v)).reduce(Integer::sum).intValue());
+        assertEquals(Arrays.asList(2,3,4,9), out3);
+
+        List<String> out4 = new ArrayList<>();
+        assertEquals(64, CQuery.from().values(input)
+            .onEach((i,v) -> out4.add(i+"#"+v))
+            .reduce(Integer::sum).intValue()
+        );
+        assertEquals(Arrays.asList("0#7", "1#6", "2#2", "3#3", "4#4", "5#9", "6#2", "7#5", "8#1", "9#6", "10#7", "11#8", "12#4"), out4);
+
+        List<String> out5 = new ArrayList<>();
+        assertEquals(18, CQuery.from().values(input)
+            .limit(4).onEach((i, v) -> out5.add(i + "#" + v))
+            .reduce(Integer::sum).intValue()
+        );
+        assertEquals(Arrays.asList("0#7", "1#6", "2#2", "3#3"), out5);
+
+        List<String> out6 = new ArrayList<>();
+        assertEquals(18, CQuery.from().values(input)
+            .onEach((i, v) -> out6.add(i + "#" + v)).limit(4)
+            .reduce(Integer::sum).intValue()
+        );
+
+        assertEquals(Arrays.asList("0#7", "1#6", "2#2", "3#3"), out6);
     }
 
 }