Skip to content

Commit

Permalink
Merge branch '3.7-dev'
Browse files Browse the repository at this point in the history
  • Loading branch information
spmallette committed Jun 28, 2024
2 parents 9592a02 + dc8f203 commit 2b3b743
Show file tree
Hide file tree
Showing 23 changed files with 261 additions and 107 deletions.
2 changes: 2 additions & 0 deletions CHANGELOG.asciidoc
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,8 @@ This release also includes changes from <<release-3-6-8, 3.6.8>>.
* Deprecated public constructor for `SeedStrategy` in favor of builder pattern to be consistent with other strategies.
* Allow specifying a customized Spark app name
* CoinStep has a getter method for its probability field
* Fixed so that TrimGlobalStep and TrimLocalStep have the same character control handling as Ltrim and Rtrim
* Fix a bug in MaxLocalStep, MinLocalStep, MeanLocalStep and SumLocalStep that it throws NoSuchElementException when encounters an empty iterator as input.
[[release-3-7-2]]
=== TinkerPop 3.7.2 (April 8, 2024)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@
import java.util.Collections;
import java.util.Set;

import static org.apache.tinkerpop.gremlin.process.traversal.step.util.StringLocalStep.getTrimmedString;

/**
* Reference implementation for lTrim() step, a mid-traversal step which returns a string with leading
* whitespace removed. Null values are not processed and remain as null when returned.
Expand All @@ -49,15 +51,7 @@ protected E map(final Traverser.Admin<S> traverser) {
}

// we will pass null values to next step
if (null == item)
return null;

int i = 0;
while (i < ((String) item).length() && Character.isWhitespace(((String) item).charAt(i))) {
i++;
}

return (E) ((String) item).substring(i);
return (E) getTrimmedString((String) item, true, false);
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -51,18 +51,9 @@ public Set<TraverserRequirement> getRequirements() {

@Override
protected E applyStringOperation(String item) {
return (E) item.substring(getIdx(item));
return (E) getTrimmedString(item, true, false);
}

@Override
public String getStepName() { return "lTrim(local)"; }

private int getIdx(final String str) {
int idx = 0;
while (idx < str.length() && Character.isWhitespace(str.charAt(idx))) {
idx++;
}
return idx;
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -21,11 +21,11 @@
import org.apache.tinkerpop.gremlin.process.traversal.Traversal;
import org.apache.tinkerpop.gremlin.process.traversal.Traverser;
import org.apache.tinkerpop.gremlin.process.traversal.traverser.TraverserRequirement;
import org.apache.tinkerpop.gremlin.process.traversal.util.FastNoSuchElementException;
import org.apache.tinkerpop.gremlin.util.iterator.IteratorUtils;

import java.util.Collections;
import java.util.Iterator;
import java.util.NoSuchElementException;
import java.util.Set;

import static org.apache.tinkerpop.gremlin.util.NumberHelper.max;
Expand All @@ -34,23 +34,26 @@
* @author Marko A. Rodriguez (http://markorodriguez.com)
* @author Daniel Kuppitz (http://gremlin.guru)
*/
public final class MaxLocalStep<E extends Comparable, S extends Iterable<E>> extends ScalarMapStep<S, E> {
public final class MaxLocalStep<E extends Comparable, S extends Iterable<E>> extends MapStep<S, E> {

public MaxLocalStep(final Traversal.Admin traversal) {
super(traversal);
}

@Override
protected E map(final Traverser.Admin<S> traverser) {
final Iterator<E> iterator = IteratorUtils.asIterator(traverser.get());
if (iterator.hasNext()) {
Comparable result = iterator.next();
while (iterator.hasNext()) {
result = max(iterator.next(), result);
protected Traverser.Admin<E> processNextStart() throws NoSuchElementException {
while (true) {
final Traverser.Admin<S> traverser = this.starts.next();
final Iterator<E> iterator = IteratorUtils.asIterator(traverser.get());

if (iterator.hasNext()) {
Comparable result = iterator.next();
while (iterator.hasNext()) {
result = max(iterator.next(), result);
}
return traverser.split((E) result, this);
}
return (E) result;
}
throw FastNoSuchElementException.instance();
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,44 +18,49 @@
*/
package org.apache.tinkerpop.gremlin.process.traversal.step.map;

import org.apache.tinkerpop.gremlin.util.NumberHelper;
import org.apache.tinkerpop.gremlin.process.traversal.Traversal;
import org.apache.tinkerpop.gremlin.process.traversal.Traverser;
import org.apache.tinkerpop.gremlin.process.traversal.traverser.TraverserRequirement;
import org.apache.tinkerpop.gremlin.process.traversal.util.FastNoSuchElementException;
import org.apache.tinkerpop.gremlin.util.iterator.IteratorUtils;

import java.util.Collections;
import java.util.Iterator;
import java.util.NoSuchElementException;
import java.util.Set;

import static org.apache.tinkerpop.gremlin.util.NumberHelper.add;
import static org.apache.tinkerpop.gremlin.util.NumberHelper.div;

/**
* @author Marko A. Rodriguez (http://markorodriguez.com)
* @author Daniel Kuppitz (http://gremlin.guru)
*/
public final class MeanLocalStep<E extends Number, S extends Iterable<E>> extends ScalarMapStep<S, Number> {
public final class MeanLocalStep<E extends Number, S extends Iterable<E>> extends MapStep<S, E> {

public MeanLocalStep(final Traversal.Admin traversal) {
super(traversal);
}

@Override
protected Number map(final Traverser.Admin<S> traverser) {
final Iterator<E> iterator = IteratorUtils.asIterator(traverser.get());
if (iterator.hasNext()) {
// forward the iterator to the first non-null or return null
E result = untilNonNull(iterator);
Long counter = 1L;
while (iterator.hasNext()) {
final Number n = iterator.next();
if (n != null) {
result = (E) NumberHelper.add(result, n);
counter++;
protected Traverser.Admin<E> processNextStart() throws NoSuchElementException {
while (true) {
final Traverser.Admin<S> traverser = this.starts.next();
final Iterator<E> iterator = IteratorUtils.asIterator(traverser.get());

if (iterator.hasNext()) {
// forward the iterator to the first non-null or return null
E result = untilNonNull(iterator);
Long counter = 1L;
while (iterator.hasNext()) {
final Number n = iterator.next();
if (n != null) {
result = (E) add(result, n);
counter++;
}
}
return traverser.split((E) div(result, counter, true), this);
}
return NumberHelper.div(result, counter, true);
}
throw FastNoSuchElementException.instance();
}

private E untilNonNull(final Iterator<E> itty) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,11 +21,11 @@
import org.apache.tinkerpop.gremlin.process.traversal.Traversal;
import org.apache.tinkerpop.gremlin.process.traversal.Traverser;
import org.apache.tinkerpop.gremlin.process.traversal.traverser.TraverserRequirement;
import org.apache.tinkerpop.gremlin.process.traversal.util.FastNoSuchElementException;
import org.apache.tinkerpop.gremlin.util.iterator.IteratorUtils;

import java.util.Collections;
import java.util.Iterator;
import java.util.NoSuchElementException;
import java.util.Set;

import static org.apache.tinkerpop.gremlin.util.NumberHelper.min;
Expand All @@ -34,23 +34,26 @@
* @author Marko A. Rodriguez (http://markorodriguez.com)
* @author Daniel Kuppitz (http://gremlin.guru)
*/
public final class MinLocalStep<E extends Comparable, S extends Iterable<E>> extends ScalarMapStep<S, E> {
public final class MinLocalStep<E extends Comparable, S extends Iterable<E>> extends MapStep<S, E> {

public MinLocalStep(final Traversal.Admin traversal) {
super(traversal);
}

@Override
protected E map(final Traverser.Admin<S> traverser) {
final Iterator<E> iterator = IteratorUtils.asIterator(traverser.get());
if (iterator.hasNext()) {
Comparable result = iterator.next();
while (iterator.hasNext()) {
result = min(iterator.next(), result);
protected Traverser.Admin<E> processNextStart() throws NoSuchElementException {
while (true) {
final Traverser.Admin<S> traverser = this.starts.next();
final Iterator<E> iterator = IteratorUtils.asIterator(traverser.get());

if (iterator.hasNext()) {
Comparable result = iterator.next();
while (iterator.hasNext()) {
result = min(iterator.next(), result);
}
return traverser.split((E) result, this);
}
return (E) result;
}
throw FastNoSuchElementException.instance();
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@
import java.util.Collections;
import java.util.Set;

import static org.apache.tinkerpop.gremlin.process.traversal.step.util.StringLocalStep.getTrimmedString;

/**
* Reference implementation for rTrim() step, a mid-traversal step which a string with trailing
* whitespace removed. Null values are not processed and remain as null when returned.
Expand All @@ -49,15 +51,7 @@ protected E map(final Traverser.Admin<S> traverser) {
}

// we will pass null values to next step
if (null == item)
return null;

int i = ((String) item).length() - 1;
while (i >= 0 && Character.isWhitespace(((String) item).charAt(i))) {
i--;
}

return (E) ((String) item).substring(0,i+1);
return (E) getTrimmedString((String) item, false, true);
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,18 +37,9 @@ public RTrimLocalStep(final Traversal.Admin traversal) {

@Override
protected E applyStringOperation(String item) {
return (E) item.substring(0,getEndIdx(item)+1);
return (E) getTrimmedString(item, false, true);
}

@Override
public String getStepName() { return "rTrim(local)"; }

private int getEndIdx(final String str) {
int idx = str.length() - 1;
while (idx >= 0 && Character.isWhitespace(str.charAt(idx))) {
idx--;
}
return idx;
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -18,39 +18,47 @@
*/
package org.apache.tinkerpop.gremlin.process.traversal.step.map;

import org.apache.tinkerpop.gremlin.util.NumberHelper;
import org.apache.tinkerpop.gremlin.process.traversal.Traversal;
import org.apache.tinkerpop.gremlin.process.traversal.Traverser;
import org.apache.tinkerpop.gremlin.process.traversal.traverser.TraverserRequirement;
import org.apache.tinkerpop.gremlin.process.traversal.util.FastNoSuchElementException;
import org.apache.tinkerpop.gremlin.util.iterator.IteratorUtils;

import java.util.Collections;
import java.util.Iterator;
import java.util.NoSuchElementException;
import java.util.Set;

import static org.apache.tinkerpop.gremlin.util.NumberHelper.add;

/**
* @author Marko A. Rodriguez (http://markorodriguez.com)
* @author Daniel Kuppitz (http://gremlin.guru)
*/
public final class SumLocalStep<E extends Number, S extends Iterable<E>> extends ScalarMapStep<S, E> {
public final class SumLocalStep<E extends Number, S extends Iterable<E>> extends MapStep<S, E> {

public SumLocalStep(final Traversal.Admin traversal) {
super(traversal);
}

@Override
protected E map(final Traverser.Admin<S> traverser) {
final Iterator<E> iterator = IteratorUtils.asIterator(traverser.get());
if (iterator.hasNext()) {
// forward the iterator to the first non-null or return null
Number result = untilNonNull(iterator);
while (iterator.hasNext()) {
result = NumberHelper.add(result, iterator.next());
protected Traverser.Admin<E> processNextStart() throws NoSuchElementException {
while (true) {
final Traverser.Admin<S> traverser = this.starts.next();
final Iterator<E> iterator = IteratorUtils.asIterator(traverser.get());

if (iterator.hasNext()) {
// forward the iterator to the first non-null or return null
E result = untilNonNull(iterator);
while (iterator.hasNext()) {
final Number n = iterator.next();
if (n != null) {
result = (E) add(result, n);
}
}
return traverser.split(result, this);
}
return (E) result;

}
throw FastNoSuchElementException.instance();
}

private E untilNonNull(final Iterator<E> itty) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@
import java.util.Collections;
import java.util.Set;

import static org.apache.tinkerpop.gremlin.process.traversal.step.util.StringLocalStep.getTrimmedString;

/**
* Reference implementation for trim() step, a mid-traversal step which returns a string with leading and trailing
* whitespace removed. Null values are not processed and remain as null when returned.
Expand All @@ -47,9 +49,7 @@ protected E map(final Traverser.Admin<S> traverser) {
throw new IllegalArgumentException(
String.format("The trim() step can only take string as argument, encountered %s", item.getClass()));
}

// we will pass null values to next step
return null == item? null : (E) ((String) item).trim();
return (E) getTrimmedString((String) item, true, true);
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ public TrimLocalStep(final Traversal.Admin traversal) {

@Override
protected E applyStringOperation(String item) {
return (E) item.trim();
return (E) getTrimmedString(item, true, true);
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,27 @@ public Set<TraverserRequirement> getRequirements() {
return Collections.singleton(TraverserRequirement.OBJECT);
}

public static String getTrimmedString(final String s, final boolean lTrim, final boolean rTrim) {
if (s == null) {
return null;
}

int start = 0;
if (lTrim) {
while (start < s.length() && Character.isWhitespace(s.charAt(start))) {
start++;
}
}

int end = s.length() - 1;
if (rTrim) {
while (end >= start && Character.isWhitespace(s.charAt(end))) {
end--;
}
}
return s.substring(start, end + 1);
}

protected abstract E applyStringOperation(final String item);

protected abstract String getStepName();
Expand Down
Loading

0 comments on commit 2b3b743

Please sign in to comment.