You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@tinkerpop.apache.org by ok...@apache.org on 2016/06/28 16:44:39 UTC
tinkerpop git commit: added RepeatUnrollStrategy for when the loop
amount is known at compile time. Fixed a bug in BranchStep around child
integration.
Repository: tinkerpop
Updated Branches:
refs/heads/TINKERPOP-1349 [created] 8753366a9
added RepeatUnrollStrategy for when the loop amount is known at compile time. Fixed a bug in BranchStep around child integration.
Project: http://git-wip-us.apache.org/repos/asf/tinkerpop/repo
Commit: http://git-wip-us.apache.org/repos/asf/tinkerpop/commit/8753366a
Tree: http://git-wip-us.apache.org/repos/asf/tinkerpop/tree/8753366a
Diff: http://git-wip-us.apache.org/repos/asf/tinkerpop/diff/8753366a
Branch: refs/heads/TINKERPOP-1349
Commit: 8753366a975101ba4edaa1888163abda3238f7ff
Parents: 0787e46
Author: Marko A. Rodriguez <ok...@gmail.com>
Authored: Tue Jun 28 10:44:32 2016 -0600
Committer: Marko A. Rodriguez <ok...@gmail.com>
Committed: Tue Jun 28 10:44:32 2016 -0600
----------------------------------------------------------------------
.../process/traversal/TraversalStrategies.java | 2 +
.../traversal/step/branch/BranchStep.java | 12 +-
.../optimization/RepeatUnrollStrategy.java | 75 +++++++++
.../IdentityRemovalStrategyTest.java | 35 ++++-
.../optimization/RepeatUnrollStrategyTest.java | 154 +++++++++++++++++++
.../process/traversal/step/map/ProfileTest.java | 36 +++--
6 files changed, 291 insertions(+), 23 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/tinkerpop/blob/8753366a/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/TraversalStrategies.java
----------------------------------------------------------------------
diff --git a/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/TraversalStrategies.java b/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/TraversalStrategies.java
index 137abb9..b093676 100644
--- a/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/TraversalStrategies.java
+++ b/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/TraversalStrategies.java
@@ -30,6 +30,7 @@ import org.apache.tinkerpop.gremlin.process.traversal.strategy.optimization.Matc
import org.apache.tinkerpop.gremlin.process.traversal.strategy.optimization.OrderLimitStrategy;
import org.apache.tinkerpop.gremlin.process.traversal.strategy.optimization.PathProcessorStrategy;
import org.apache.tinkerpop.gremlin.process.traversal.strategy.optimization.RangeByIsCountStrategy;
+import org.apache.tinkerpop.gremlin.process.traversal.strategy.optimization.RepeatUnrollStrategy;
import org.apache.tinkerpop.gremlin.process.traversal.strategy.verification.ComputerVerificationStrategy;
import org.apache.tinkerpop.gremlin.process.traversal.strategy.verification.StandardVerificationStrategy;
import org.apache.tinkerpop.gremlin.process.traversal.util.DefaultTraversalStrategies;
@@ -193,6 +194,7 @@ public interface TraversalStrategies extends Serializable, Cloneable {
FilterRankingStrategy.instance(),
IdentityRemovalStrategy.instance(),
MatchPredicateStrategy.instance(),
+ RepeatUnrollStrategy.instance(),
RangeByIsCountStrategy.instance(),
ProfileStrategy.instance(),
StandardVerificationStrategy.instance());
http://git-wip-us.apache.org/repos/asf/tinkerpop/blob/8753366a/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/branch/BranchStep.java
----------------------------------------------------------------------
diff --git a/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/branch/BranchStep.java b/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/branch/BranchStep.java
index 2cd954d..19df2a6 100644
--- a/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/branch/BranchStep.java
+++ b/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/branch/BranchStep.java
@@ -165,18 +165,22 @@ public class BranchStep<S, E, M> extends ComputerAwareStep<S, E> implements Trav
final List<Traversal.Admin<S, E>> clonedTraversals = clone.traversalOptions.compute(entry.getKey(), (k, v) ->
(v == null) ? new ArrayList<>(traversals.size()) : v);
for (final Traversal.Admin<S, E> traversal : traversals) {
- final Traversal.Admin<S, E> clonedTraversal = traversal.clone();
- clonedTraversals.add(clonedTraversal);
- clone.integrateChild(clonedTraversal);
+ clonedTraversals.add(traversal.clone());
}
}
}
clone.branchTraversal = this.branchTraversal.clone();
- clone.integrateChild(clone.branchTraversal);
return clone;
}
@Override
+ public void setTraversal(final Traversal.Admin<?, ?> parentTraversal) {
+ super.setTraversal(parentTraversal);
+ this.integrateChild(this.branchTraversal);
+ this.traversalOptions.values().stream().flatMap(List::stream).forEach(this::integrateChild);
+ }
+
+ @Override
public int hashCode() {
int result = super.hashCode();
if (this.traversalOptions != null)
http://git-wip-us.apache.org/repos/asf/tinkerpop/blob/8753366a/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/strategy/optimization/RepeatUnrollStrategy.java
----------------------------------------------------------------------
diff --git a/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/strategy/optimization/RepeatUnrollStrategy.java b/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/strategy/optimization/RepeatUnrollStrategy.java
new file mode 100644
index 0000000..9047478
--- /dev/null
+++ b/gremlin-core/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/strategy/optimization/RepeatUnrollStrategy.java
@@ -0,0 +1,75 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.tinkerpop.gremlin.process.traversal.strategy.optimization;
+
+import org.apache.tinkerpop.gremlin.process.traversal.Step;
+import org.apache.tinkerpop.gremlin.process.traversal.Traversal;
+import org.apache.tinkerpop.gremlin.process.traversal.TraversalStrategy;
+import org.apache.tinkerpop.gremlin.process.traversal.lambda.LoopTraversal;
+import org.apache.tinkerpop.gremlin.process.traversal.step.branch.RepeatStep;
+import org.apache.tinkerpop.gremlin.process.traversal.step.map.NoOpBarrierStep;
+import org.apache.tinkerpop.gremlin.process.traversal.strategy.AbstractTraversalStrategy;
+import org.apache.tinkerpop.gremlin.process.traversal.util.TraversalHelper;
+
+/**
+ * @author Marko A. Rodriguez (http://markorodriguez.com)
+ */
+public final class RepeatUnrollStrategy extends AbstractTraversalStrategy<TraversalStrategy.OptimizationStrategy> implements TraversalStrategy.OptimizationStrategy {
+
+ private static final RepeatUnrollStrategy INSTANCE = new RepeatUnrollStrategy();
+
+ private RepeatUnrollStrategy() {
+ }
+
+ @Override
+ public void apply(final Traversal.Admin<?, ?> traversal) {
+ if (!TraversalHelper.hasStepOfAssignableClass(RepeatStep.class, traversal) ||
+ TraversalHelper.onGraphComputer(traversal))
+ return;
+
+ for (int i = 0; i < traversal.getSteps().size(); i++) {
+ if (traversal.getSteps().get(i) instanceof RepeatStep) {
+ final RepeatStep<?> repeatStep = (RepeatStep) traversal.getSteps().get(i);
+ if (null == repeatStep.getEmitTraversal() && repeatStep.getUntilTraversal() instanceof LoopTraversal) {
+ final Traversal.Admin<?, ?> repeatTraversal = repeatStep.getGlobalChildren().get(0);
+ final int repeatLength = repeatTraversal.getSteps().size() - 1;
+ repeatTraversal.removeStep(repeatLength);
+ int insertIndex = i;
+ final int loops = (int) ((LoopTraversal) repeatStep.getUntilTraversal()).getMaxLoops();
+ for (int j = 0; j < loops; j++) {
+ TraversalHelper.insertTraversal(insertIndex, repeatTraversal.clone(), traversal); // removes the RepeatEndStep
+ insertIndex = insertIndex + repeatLength + 1;
+ traversal.addStep(insertIndex, new NoOpBarrierStep<>(traversal));
+ }
+ if (!repeatStep.getLabels().isEmpty()) {
+ final Step<?, ?> lastStep = (Step) traversal.getSteps().get(insertIndex);
+ repeatStep.getLabels().forEach(lastStep::addLabel);
+ }
+ traversal.removeStep(i); // remove the RepeatStep
+ }
+ }
+ }
+ }
+
+
+ public static RepeatUnrollStrategy instance() {
+ return INSTANCE;
+ }
+}
http://git-wip-us.apache.org/repos/asf/tinkerpop/blob/8753366a/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/strategy/optimization/IdentityRemovalStrategyTest.java
----------------------------------------------------------------------
diff --git a/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/strategy/optimization/IdentityRemovalStrategyTest.java b/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/strategy/optimization/IdentityRemovalStrategyTest.java
index fd1ec2b..c71ad99 100644
--- a/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/strategy/optimization/IdentityRemovalStrategyTest.java
+++ b/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/strategy/optimization/IdentityRemovalStrategyTest.java
@@ -22,6 +22,7 @@ import org.apache.tinkerpop.gremlin.process.traversal.Traversal;
import org.apache.tinkerpop.gremlin.process.traversal.TraversalStrategies;
import org.apache.tinkerpop.gremlin.process.traversal.dsl.graph.__;
import org.apache.tinkerpop.gremlin.process.traversal.util.DefaultTraversalStrategies;
+import org.apache.tinkerpop.gremlin.util.TimeUtil;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;
@@ -29,6 +30,8 @@ import org.junit.runners.Parameterized;
import java.util.Arrays;
import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+
/**
* @author Marko A. Rodriguez (http://markorodriguez.com)
@@ -36,6 +39,8 @@ import static org.junit.Assert.assertEquals;
@RunWith(Parameterized.class)
public class IdentityRemovalStrategyTest {
+ private static boolean executedshouldBeFaster = false;
+
@Parameterized.Parameter(value = 0)
public Traversal original;
@@ -43,7 +48,7 @@ public class IdentityRemovalStrategyTest {
public Traversal optimized;
- void applyIdentityRemovalStrategy(final Traversal traversal) {
+ private void applyIdentityRemovalStrategy(final Traversal traversal) {
final TraversalStrategies strategies = new DefaultTraversalStrategies();
strategies.addStrategies(IdentityRemovalStrategy.instance());
traversal.asAdmin().setStrategies(strategies);
@@ -70,4 +75,30 @@ public class IdentityRemovalStrategyTest {
{__.out().identity().as("a").out().in().identity().identity().as("b").identity().out(), __.out().as("a").out().in().as("b").out()},
});
}
-}
\ No newline at end of file
+
+ @Test
+ public void shouldBeFaster() {
+ if (executedshouldBeFaster)
+ return;
+ else
+ executedshouldBeFaster = true;
+ final int startSize = 1000;
+ final int clockRuns = 1000;
+ final Integer[] starts = new Integer[startSize];
+ for (int i = 0; i < startSize; i++) {
+ starts[i] = i;
+ }
+
+ final Runnable original = () -> __.inject(starts).identity().identity().identity().identity().iterate();
+
+ final Runnable optimized = () -> {
+ final Traversal<Integer, Integer> traversal = __.inject(starts).identity().identity().identity().identity();
+ traversal.asAdmin().setStrategies(traversal.asAdmin().getStrategies().clone().addStrategies(IdentityRemovalStrategy.instance()));
+ traversal.iterate();
+ };
+
+ //System.out.println(TimeUtil.clock(clockRuns, original) + "---" + TimeUtil.clock(clockRuns,optimized));
+ assertTrue(TimeUtil.clock(clockRuns, original) > TimeUtil.clock(clockRuns, optimized));
+ assertTrue(TimeUtil.clock(clockRuns, optimized) < TimeUtil.clock(clockRuns, original));
+ }
+}
http://git-wip-us.apache.org/repos/asf/tinkerpop/blob/8753366a/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/strategy/optimization/RepeatUnrollStrategyTest.java
----------------------------------------------------------------------
diff --git a/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/strategy/optimization/RepeatUnrollStrategyTest.java b/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/strategy/optimization/RepeatUnrollStrategyTest.java
new file mode 100644
index 0000000..1c4c4b7
--- /dev/null
+++ b/gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/process/traversal/strategy/optimization/RepeatUnrollStrategyTest.java
@@ -0,0 +1,154 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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.tinkerpop.gremlin.process.traversal.strategy.optimization;
+
+import org.apache.tinkerpop.gremlin.process.traversal.Traversal;
+import org.apache.tinkerpop.gremlin.process.traversal.TraversalStrategies;
+import org.apache.tinkerpop.gremlin.process.traversal.Traverser;
+import org.apache.tinkerpop.gremlin.process.traversal.dsl.graph.__;
+import org.apache.tinkerpop.gremlin.process.traversal.util.DefaultTraversalStrategies;
+import org.apache.tinkerpop.gremlin.structure.Vertex;
+import org.apache.tinkerpop.gremlin.util.TimeUtil;
+import org.javatuples.Pair;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.junit.runners.Parameterized;
+
+import java.util.Arrays;
+import java.util.HashSet;
+import java.util.Random;
+import java.util.function.Predicate;
+import java.util.function.Supplier;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+
+/**
+ * @author Marko A. Rodriguez (http://markorodriguez.com)
+ */
+@RunWith(Parameterized.class)
+public class RepeatUnrollStrategyTest {
+
+ private static final Random RANDOM = new Random();
+ private static boolean shouldBeFasterWithUniqueStreamExecuted = false;
+ private static boolean shouldBeFasterWithDuplicateStreamExecuted = false;
+
+ @Parameterized.Parameter(value = 0)
+ public Traversal original;
+
+ @Parameterized.Parameter(value = 1)
+ public Traversal optimized;
+
+
+ private void applyRepeatUnrollStrategy(final Traversal traversal) {
+ final TraversalStrategies strategies = new DefaultTraversalStrategies();
+ strategies.addStrategies(RepeatUnrollStrategy.instance());
+ traversal.asAdmin().setStrategies(strategies);
+ traversal.asAdmin().applyStrategies();
+
+ }
+
+ @Test
+ public void doTest() {
+ applyRepeatUnrollStrategy(original);
+ assertEquals(optimized, original);
+ }
+
+ @Parameterized.Parameters(name = "{0}")
+ public static Iterable<Object[]> generateTestParameters() {
+
+ final Predicate<Traverser<Vertex>> predicate = t -> t.loops() > 5;
+ return Arrays.asList(new Traversal[][]{
+ {__.identity(), __.identity()},
+ {__.out().as("a").in().repeat(__.outE("created").bothV()).times(2).in(), __.out().as("a").in().outE("created").bothV().barrier().outE("created").bothV().barrier().in()},
+ {__.out().repeat(__.outE("created").bothV()).times(1).in(), __.out().outE("created").bothV().barrier().in()},
+ {__.repeat(__.outE("created").bothV()).times(1).in(), __.outE("created").bothV().barrier().in()},
+ {__.repeat(__.out()).times(2).as("x").repeat(__.in().as("b")).times(3), __.out().barrier().out().barrier().as("x").in().as("b").barrier().in().as("b").barrier().in().as("b").barrier()},
+ {__.repeat(__.outE("created").inV()).times(2), __.outE("created").inV().barrier().outE("created").inV().barrier()},
+ {__.repeat(__.out()).times(3), __.out().barrier().out().barrier().out().barrier()},
+ {__.repeat(__.local(__.select("a").out("knows"))).times(2), __.local(__.select("a").out("knows")).barrier().local(__.select("a").out("knows")).barrier()},
+ {__.<Vertex>times(2).repeat(__.out()), __.out().barrier().out().barrier()},
+ {__.<Vertex>out().times(2).repeat(__.out().as("a")).as("x"), __.out().out().as("a").barrier().out().as("a").barrier().as("x")},
+ {__.repeat(__.out()).emit().times(2), __.repeat(__.out()).emit().times(2)},
+ {__.repeat(__.out()).until(predicate), __.repeat(__.out()).until(predicate)},
+ {__.repeat(__.out()).until(predicate).repeat(__.out()).times(2), __.repeat(__.out()).until(predicate).out().barrier().out().barrier()},
+ {__.repeat(__.union(__.both(), __.identity())).times(2).out(), __.union(__.both(), __.identity()).barrier().union(__.both(), __.identity()).barrier().out()},
+ });
+ }
+
+ @Test
+ public void shouldBeFasterWithUniqueStream() {
+ if (shouldBeFasterWithUniqueStreamExecuted)
+ return;
+ shouldBeFasterWithUniqueStreamExecuted = true;
+ final int startSize = 1000;
+ final int clockRuns = 1000;
+ final Integer[] starts = new Integer[startSize];
+ for (int i = 0; i < startSize; i++) {
+ starts[i] = i; // 1000 unique objects
+ }
+ assertEquals(startSize, new HashSet<>(Arrays.asList(starts)).size());
+ clockTraversals(starts, clockRuns);
+ }
+
+ @Test
+ public void shouldBeFasterWithDuplicateStream() {
+ if (shouldBeFasterWithDuplicateStreamExecuted)
+ return;
+ shouldBeFasterWithDuplicateStreamExecuted = true;
+ final int startSize = 1000;
+ final int clockRuns = 1000;
+ final int uniques = 100;
+ final Integer[] starts = new Integer[startSize];
+ for (int i = 0; i < startSize; i++) {
+ starts[i] = i % uniques; // 100 unique objects
+ }
+ assertEquals(uniques, new HashSet<>(Arrays.asList(starts)).size());
+ clockTraversals(starts, clockRuns);
+ }
+
+ private void clockTraversals(final Integer[] starts, final int clockRuns) {
+ final int times = RANDOM.nextInt(4) + 2;
+ assertTrue(times > 1 && times < 6);
+ final Supplier<Long> original = () -> __.inject(starts).repeat(__.identity()).times(times).<Long>sum().next();
+
+ final TraversalStrategies strategies = new DefaultTraversalStrategies();
+ strategies.addStrategies(RepeatUnrollStrategy.instance());
+ final Supplier<Long> optimized = () -> {
+ final Traversal<Integer, Long> traversal = __.inject(starts).repeat(__.identity()).times(times).sum();
+ traversal.asAdmin().setStrategies(strategies);
+ return traversal.next();
+ };
+
+ final Pair<Double, Long> originalResult;
+ final Pair<Double, Long> optimizedResult;
+ if (RANDOM.nextBoolean()) {
+ originalResult = TimeUtil.clockWithResult(clockRuns, original);
+ optimizedResult = TimeUtil.clockWithResult(clockRuns, optimized);
+ } else {
+ optimizedResult = TimeUtil.clockWithResult(clockRuns, optimized);
+ originalResult = TimeUtil.clockWithResult(clockRuns, original);
+ }
+
+ // System.out.println(originalResult + "---" + optimizedResult);
+ assertEquals(originalResult.getValue1(), optimizedResult.getValue1());
+ assertTrue(originalResult.getValue0() > optimizedResult.getValue0());
+ }
+}
http://git-wip-us.apache.org/repos/asf/tinkerpop/blob/8753366a/gremlin-test/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/ProfileTest.java
----------------------------------------------------------------------
diff --git a/gremlin-test/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/ProfileTest.java b/gremlin-test/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/ProfileTest.java
index 4d0ce49..548e7ab 100644
--- a/gremlin-test/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/ProfileTest.java
+++ b/gremlin-test/src/main/java/org/apache/tinkerpop/gremlin/process/traversal/step/map/ProfileTest.java
@@ -33,6 +33,8 @@ import org.apache.tinkerpop.gremlin.process.traversal.dsl.graph.__;
import org.apache.tinkerpop.gremlin.process.traversal.step.Profiling;
import org.apache.tinkerpop.gremlin.process.traversal.step.util.ProfileStep;
import org.apache.tinkerpop.gremlin.process.traversal.strategy.optimization.RangeByIsCountStrategy;
+import org.apache.tinkerpop.gremlin.process.traversal.strategy.optimization.RepeatUnrollStrategy;
+import org.apache.tinkerpop.gremlin.process.traversal.strategy.verification.ComputerVerificationStrategy;
import org.apache.tinkerpop.gremlin.process.traversal.strategy.verification.VerificationException;
import org.apache.tinkerpop.gremlin.process.traversal.util.Metrics;
import org.apache.tinkerpop.gremlin.process.traversal.util.MutableMetrics;
@@ -231,7 +233,9 @@ public abstract class ProfileTest extends AbstractGremlinProcessTest {
printTraversalForm(traversal);
final TraversalMetrics traversalMetrics = traversal.next();
- validate_g_V_repeat_both_modern_profile(traversalMetrics);
+ validate_g_V_repeat_both_modern_profile(traversalMetrics,
+ traversal.asAdmin().getStrategies().toList().contains(RepeatUnrollStrategy.instance()) &&
+ !traversal.asAdmin().getStrategies().toList().contains(ComputerVerificationStrategy.instance()));
}
@Test
@@ -241,10 +245,12 @@ public abstract class ProfileTest extends AbstractGremlinProcessTest {
printTraversalForm(traversal);
traversal.iterate();
final TraversalMetrics traversalMetrics = traversal.asAdmin().getSideEffects().<TraversalMetrics>get(METRICS_KEY);
- validate_g_V_repeat_both_modern_profile(traversalMetrics);
+ validate_g_V_repeat_both_modern_profile(traversalMetrics,
+ traversal.asAdmin().getStrategies().toList().contains(RepeatUnrollStrategy.instance()) &&
+ !traversal.asAdmin().getStrategies().toList().contains(ComputerVerificationStrategy.instance()));
}
- private void validate_g_V_repeat_both_modern_profile(TraversalMetrics traversalMetrics) {
+ private void validate_g_V_repeat_both_modern_profile(TraversalMetrics traversalMetrics, boolean withRepeatUnrollStrategy) {
traversalMetrics.toString(); // ensure no exceptions are thrown
Metrics metrics = traversalMetrics.getMetrics(0);
@@ -252,25 +258,21 @@ public abstract class ProfileTest extends AbstractGremlinProcessTest {
assertEquals(6, metrics.getCount(TraversalMetrics.ELEMENT_COUNT_ID).longValue());
metrics = traversalMetrics.getMetrics(1);
- assertEquals(72, metrics.getCount(TraversalMetrics.ELEMENT_COUNT_ID).longValue());
+ assertEquals(withRepeatUnrollStrategy ? 12 : 72, metrics.getCount(TraversalMetrics.ELEMENT_COUNT_ID).longValue());
assertNotEquals(0, metrics.getCount(TraversalMetrics.TRAVERSER_COUNT_ID).longValue());
- assertTrue("Count should be greater than traversers.", metrics.getCount(TraversalMetrics.ELEMENT_COUNT_ID) > metrics.getCount(TraversalMetrics.TRAVERSER_COUNT_ID).longValue());
+ if (!withRepeatUnrollStrategy)
+ assertTrue("Count should be greater than traversers.", metrics.getCount(TraversalMetrics.ELEMENT_COUNT_ID) > metrics.getCount(TraversalMetrics.TRAVERSER_COUNT_ID).longValue());
assertTrue("Percent duration should be positive.", (Double) metrics.getAnnotation(TraversalMetrics.PERCENT_DURATION_KEY) >= 0);
assertTrue("Times should be positive.", metrics.getDuration(TimeUnit.MICROSECONDS) >= 0);
// Test the nested global metrics of the repeat step
- final Metrics vertexStepNestedInRepeat = (Metrics) metrics.getNested().toArray()[0];
- assertEquals(114, vertexStepNestedInRepeat.getCount(TraversalMetrics.ELEMENT_COUNT_ID).longValue());
- assertNotEquals(0, vertexStepNestedInRepeat.getCount(TraversalMetrics.TRAVERSER_COUNT_ID).longValue());
- assertTrue("Count should be greater than traversers.", vertexStepNestedInRepeat.getCount(TraversalMetrics.ELEMENT_COUNT_ID) > vertexStepNestedInRepeat.getCount(TraversalMetrics.TRAVERSER_COUNT_ID).longValue());
- assertTrue("Times should be positive.", vertexStepNestedInRepeat.getDuration(TimeUnit.MICROSECONDS) >= 0);
-
- /*final Metrics repeatEndStepNestedInRepeat = (Metrics) metrics.getNested().toArray()[1];
- assertEquals(72, repeatEndStepNestedInRepeat.getCount(TraversalMetrics.ELEMENT_COUNT_ID).longValue());
- assertNotEquals(0, repeatEndStepNestedInRepeat.getCount(TraversalMetrics.TRAVERSER_COUNT_ID).longValue());
- assertTrue("Count should be greater than traversers.", repeatEndStepNestedInRepeat.getCount(TraversalMetrics.ELEMENT_COUNT_ID) > repeatEndStepNestedInRepeat.getCount(TraversalMetrics.TRAVERSER_COUNT_ID).longValue());
- assertTrue("Times should be positive.", repeatEndStepNestedInRepeat.getDuration(TimeUnit.MICROSECONDS) >= 0);*/
-
+ if (!withRepeatUnrollStrategy) {
+ final Metrics vertexStepNestedInRepeat = (Metrics) metrics.getNested().toArray()[0];
+ assertEquals(114, vertexStepNestedInRepeat.getCount(TraversalMetrics.ELEMENT_COUNT_ID).longValue());
+ assertNotEquals(0, vertexStepNestedInRepeat.getCount(TraversalMetrics.TRAVERSER_COUNT_ID).longValue());
+ assertTrue("Count should be greater than traversers.", vertexStepNestedInRepeat.getCount(TraversalMetrics.ELEMENT_COUNT_ID) > vertexStepNestedInRepeat.getCount(TraversalMetrics.TRAVERSER_COUNT_ID).longValue());
+ assertTrue("Times should be positive.", vertexStepNestedInRepeat.getDuration(TimeUnit.MICROSECONDS) >= 0);
+ }
double totalPercentDuration = 0;
for (Metrics m : traversalMetrics.getMetrics()) {