You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@tapestry.apache.org by hl...@apache.org on 2010/06/03 19:21:56 UTC
svn commit: r951074 - in /tapestry/tapestry5/trunk/tapestry-func/src:
main/java/org/apache/tapestry5/func/ test/java/org/apache/tapestry5/func/
Author: hlship
Date: Thu Jun 3 17:21:55 2010
New Revision: 951074
URL: http://svn.apache.org/viewvc?rev=951074&view=rev
Log:
Add a drop() method to Flow
Added:
tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/LazyDrop.java (contents, props changed)
- copied, changed from r950889, tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/FuncAssert.java
tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/BaseFuncTest.java (with props)
tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/TakeDropTests.java (with props)
Removed:
tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/FuncAssert.java
tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/TakeTests.java
Modified:
tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/AbstractFlow.java
tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/ArrayFlow.java
tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/EmptyFlow.java
tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/Flow.java
tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/FuncTest.java
tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/RangeTests.java
Modified: tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/AbstractFlow.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/AbstractFlow.java?rev=951074&r1=951073&r2=951074&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/AbstractFlow.java (original)
+++ tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/AbstractFlow.java Thu Jun 3 17:21:55 2010
@@ -201,4 +201,13 @@ abstract class AbstractFlow<T> implement
return F.lazy(new LazyTake<T>(length, this));
}
+ public Flow<T> drop(int length)
+ {
+ assert length >= 0;
+
+ if (length == 0)
+ return this;
+
+ return F.lazy(new LazyDrop<T>(length, this));
+ }
}
Modified: tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/ArrayFlow.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/ArrayFlow.java?rev=951074&r1=951073&r2=951074&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/ArrayFlow.java (original)
+++ tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/ArrayFlow.java Thu Jun 3 17:21:55 2010
@@ -186,4 +186,16 @@ class ArrayFlow<T> extends AbstractFlow<
return new ArrayFlow<T>(values, start, Math.min(count, length));
}
+ public Flow<T> drop(int length)
+ {
+ assert length >= 0;
+
+ if (length == 0)
+ return this;
+
+ if (length >= count)
+ return F.emptyFlow();
+
+ return new ArrayFlow<T>(values, start + length, count - length);
+ }
}
Modified: tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/EmptyFlow.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/EmptyFlow.java?rev=951074&r1=951073&r2=951074&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/EmptyFlow.java (original)
+++ tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/EmptyFlow.java Thu Jun 3 17:21:55 2010
@@ -115,4 +115,9 @@ class EmptyFlow<T> extends AbstractFlow<
{
return this;
}
+
+ public Flow<T> drop(int length)
+ {
+ return this;
+ }
}
Modified: tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/Flow.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/Flow.java?rev=951074&r1=951073&r2=951074&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/Flow.java (original)
+++ tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/Flow.java Thu Jun 3 17:21:55 2010
@@ -18,7 +18,7 @@ import java.util.Comparator;
import java.util.List;
/**
- * A Flow is a a functional interface for working with a ordered collection of values.
+ * A Flow is a a functional interface for working with an ordered collection of values.
* A given Flow contains only values of a particular type. Standard operations allow for
* filtering the Flow, or appending values to the Flow. Since Flows are immutable, all operations
* on Flows return new immutable Flows. Flows are thread safe (to the extent that the {@link Mapper}s, {@link Predicate}
@@ -26,11 +26,15 @@ import java.util.List;
* Flows are <em>lazy</em>: filtering, mapping, and concatenating Flows will do so with no, or a minimum, of evaluation.
* However, converting a Flow into a {@link List} will force a realization of the entire Flow.
* <p>
+ * In some cases, a Flow may be an infinite, lazily evaluated sequence. Operations that iterate over all values (such as
+ * {@link #count()} or {@link #reduce(Reducer, Object)}) may become infinite loops.
+ * <p>
* Using Flows allows for a very fluid interface.
* <p>
* Flows are initially created using {@link F#flow(java.util.Collection)} or {@link F#flow(Object...)}.
*
* @since 5.2.0
+ * @see F#lazy(LazyFunction)
*/
public interface Flow<T> extends Iterable<T>
{
@@ -131,4 +135,12 @@ public interface Flow<T> extends Iterabl
* maximum number of values in the Flow
*/
Flow<T> take(int length);
+
+ /**
+ * Returns a new Flow with the first values omitted.
+ *
+ * @param length
+ * number of values to drop
+ */
+ Flow<T> drop(int length);
}
Copied: tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/LazyDrop.java (from r950889, tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/FuncAssert.java)
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/LazyDrop.java?p2=tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/LazyDrop.java&p1=tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/FuncAssert.java&r1=950889&r2=951074&rev=951074&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/FuncAssert.java (original)
+++ tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/LazyDrop.java Thu Jun 3 17:21:55 2010
@@ -14,27 +14,34 @@
package org.apache.tapestry5.func;
-import java.util.Arrays;
-import java.util.List;
-
-import org.testng.Assert;
-
-public class FuncAssert extends Assert
+class LazyDrop<T> implements LazyFunction<T>
{
+ private final int length;
- protected <T> void assertFlowValues(Flow<T> actual, T... expected)
- {
- assertListsEquals(actual.toList(), expected);
- }
+ private Flow<T> flow;
- protected <T> void assertListsEquals(List<T> actual, T... expected)
+ public LazyDrop(int length, Flow<T> flow)
{
- assertEquals(actual, Arrays.asList(expected));
+ this.length = length;
+ this.flow = flow;
}
- protected void unreachable()
+ public LazyContinuation<T> next()
{
- throw new RuntimeException("Should not be reachable.");
+ for (int i = 0; i < length; i++)
+ {
+ if (flow.isEmpty())
+ return null;
+
+ flow = flow.rest();
+ }
+
+ // The case where the flow contains exactly length values.
+
+ if (flow.isEmpty())
+ return null;
+
+ return new LazyContinuation<T>(flow.first(), new LazyIterate<T>(flow.rest()));
}
}
Propchange: tapestry/tapestry5/trunk/tapestry-func/src/main/java/org/apache/tapestry5/func/LazyDrop.java
------------------------------------------------------------------------------
svn:eol-style = native
Added: tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/BaseFuncTest.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/BaseFuncTest.java?rev=951074&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/BaseFuncTest.java (added)
+++ tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/BaseFuncTest.java Thu Jun 3 17:21:55 2010
@@ -0,0 +1,66 @@
+// Copyright 2010 The Apache Software Foundation
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package org.apache.tapestry5.func;
+
+import java.util.Arrays;
+import java.util.List;
+
+import org.testng.Assert;
+
+public class BaseFuncTest extends Assert
+{
+
+ protected Mapper<String, Integer> stringToLength = new Mapper<String, Integer>()
+ {
+ public Integer map(String input)
+ {
+ return input.length();
+ }
+ };
+
+ protected Mapper<Integer, Boolean> toEven = new Mapper<Integer, Boolean>()
+ {
+ public Boolean map(Integer input)
+ {
+ return evenp.accept(input);
+ }
+ };
+
+ protected Predicate<Number> evenp = new Predicate<Number>()
+ {
+ public boolean accept(Number object)
+ {
+ return object.longValue() % 2 == 0;
+ };
+ };
+
+ protected Flow<Integer> filteredEmpty = F.flow(1, 3, 5, 7).filter(evenp);
+
+ protected <T> void assertFlowValues(Flow<T> actual, T... expected)
+ {
+ assertListsEquals(actual.toList(), expected);
+ }
+
+ protected <T> void assertListsEquals(List<T> actual, T... expected)
+ {
+ assertEquals(actual, Arrays.asList(expected));
+ }
+
+ protected void unreachable()
+ {
+ throw new RuntimeException("Should not be reachable.");
+ }
+
+}
Propchange: tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/BaseFuncTest.java
------------------------------------------------------------------------------
svn:eol-style = native
Modified: tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/FuncTest.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/FuncTest.java?rev=951074&r1=951073&r2=951074&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/FuncTest.java (original)
+++ tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/FuncTest.java Thu Jun 3 17:21:55 2010
@@ -21,37 +21,23 @@ import java.util.Iterator;
import java.util.List;
import java.util.Locale;
-import org.testng.Assert;
import org.testng.annotations.Test;
-public class FuncTest extends FuncAssert
+public class FuncTest extends BaseFuncTest
{
-
- private Mapper<String, Integer> stringToLength = new Mapper<String, Integer>()
+ protected Mapper<Integer, Flow<Integer>> sequencer = new Mapper<Integer, Flow<Integer>>()
{
- public Integer map(String input)
- {
- return input.length();
- }
- };
- private Mapper<Integer, Boolean> toEven = new Mapper<Integer, Boolean>()
- {
- public Boolean map(Integer input)
+ public Flow<Integer> map(Integer value)
{
- return evenp.accept(input);
- }
- };
+ Flow<Integer> flow = F.flow();
- private Predicate<Number> evenp = new Predicate<Number>()
- {
- public boolean accept(Number object)
- {
- return object.longValue() % 2 == 0;
- };
- };
+ for (int i = 0; i < value; i++)
+ flow = flow.append(value);
- private Flow<Integer> filteredEmpty = F.flow(1, 3, 5, 7).filter(evenp);
+ return flow;
+ }
+ };
@Test
public void map()
@@ -585,20 +571,6 @@ public class FuncTest extends FuncAssert
}, initial), initial);
}
- private Mapper<Integer, Flow<Integer>> sequencer = new Mapper<Integer, Flow<Integer>>()
- {
-
- public Flow<Integer> map(Integer value)
- {
- Flow<Integer> flow = F.flow();
-
- for (int i = 0; i < value; i++)
- flow = flow.append(value);
-
- return flow;
- }
- };
-
@Test
public void mapcat_on_empty_flow_is_empty()
{
Modified: tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/RangeTests.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/RangeTests.java?rev=951074&r1=951073&r2=951074&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/RangeTests.java (original)
+++ tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/RangeTests.java Thu Jun 3 17:21:55 2010
@@ -16,7 +16,7 @@ package org.apache.tapestry5.func;
import org.testng.annotations.Test;
-public class RangeTests extends FuncAssert
+public class RangeTests extends BaseFuncTest
{
@Test
public void empty_range_if_values_equal()
@@ -44,4 +44,12 @@ public class RangeTests extends FuncAsse
assertFlowValues(series.take(5), 3, 8, 13, 18, 23);
}
+
+ @Test
+ public void filtered_series()
+ {
+ Flow<Integer> series = F.series(1, 1);
+
+ assertFlowValues(series.filter(evenp).take(4), 2, 4, 6, 8);
+ }
}
Added: tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/TakeDropTests.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/TakeDropTests.java?rev=951074&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/TakeDropTests.java (added)
+++ tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/TakeDropTests.java Thu Jun 3 17:21:55 2010
@@ -0,0 +1,93 @@
+// Copyright 2010 The Apache Software Foundation
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package org.apache.tapestry5.func;
+
+import org.testng.annotations.Test;
+
+public class TakeDropTests extends BaseFuncTest
+{
+ @Test
+ public void take_from_empty_list()
+ {
+ assertSame(F.flow().take(34), F.EMPTY_FLOW);
+ }
+
+ @Test
+ public void take_from_flow()
+ {
+ assertFlowValues(F.series(1, 1).remove(evenp).take(2), 1, 3);
+ }
+
+ @Test
+ public void take_from_array_flow()
+ {
+ Flow<Integer> flow = F.flow(1, 2, 3, 4, 5);
+
+ assertFlowValues(flow.take(2), 1, 2);
+
+ assertFlowValues(flow.take(99), 1, 2, 3, 4, 5);
+
+ assertSame(flow.take(0), F.EMPTY_FLOW);
+ }
+
+ @Test
+ public void take_and_drop()
+ {
+ // This can go much, much larger but starts taking a while. Don't hold a reference to the start
+ // of the series or it can run out of memory.
+ int length = 100000;
+
+ assertFlowValues(F.series(1, 1).filter(evenp).drop(length).take(3), 2 * length + 2, 2 * length + 4,
+ 2 * length + 6);
+ }
+
+ @Test
+ public void drop_from_empty_is_empty()
+ {
+ assertSame(F.flow().drop(99), F.EMPTY_FLOW);
+ }
+
+ @Test
+ public void drop_exact_size_of_flow_is_empty()
+ {
+ assertTrue(F.range(1, 10).filter(evenp).drop(4).isEmpty());
+ }
+
+ @Test
+ public void lazy_drop_more_than_available()
+ {
+ assertTrue(F.range(1, 10).filter(evenp).drop(5).isEmpty());
+ }
+
+ @Test
+ public void drop_all_from_array_flow_is_empty_flow()
+ {
+ assertSame(F.flow(1, 2, 3).drop(3), F.EMPTY_FLOW);
+ }
+
+ @Test
+ public void drop_zero_from_array_flow_is_same()
+ {
+ Flow<Integer> flow = F.flow(1, 2, 3);
+
+ assertSame(flow.drop(0), flow);
+ }
+
+ @Test
+ public void drop_from_array_flow()
+ {
+ assertFlowValues(F.range(1, 10).reverse().drop(2), 7, 6, 5, 4, 3, 2, 1);
+ }
+}
Propchange: tapestry/tapestry5/trunk/tapestry-func/src/test/java/org/apache/tapestry5/func/TakeDropTests.java
------------------------------------------------------------------------------
svn:eol-style = native