Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adding coordAll() versions for Feature, FeatureCollection, and Geometry parameters #1009

Merged

Conversation

langsmith
Copy link

This pr adds methods for getting a List<Point> from a Feature, FeatureCollection, or Geometry. These parameters were missing from our Turf for Java library, but are part of https://turfjs.org/docs/#coordAll .

Having these methods will be incredibly helpful for adding a number of new Turf methods to our Turf for Java library. Also unblocks #1007.

@langsmith langsmith requested a review from osana April 22, 2019 18:36
@langsmith langsmith self-assigned this Apr 22, 2019
@langsmith langsmith force-pushed the ls-adding-coordAll-for-Feature-and-FeatureCollection branch 3 times, most recently from 3224727 to 716bc2f Compare April 22, 2019 23:49
* @since 4.7.0
*/
public static List<Point> coordAll(@NonNull Feature feature) {
return coordAll(FeatureCollection.fromFeature(feature));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The library should not add overhead. No need to create FeatureCreation.

public static List<Point> coordAll(@NonNull FeatureCollection featureCollection) {
List<Point> finalCoordsList = new ArrayList<>();
for (Feature singleFeature : featureCollection.features()) {
finalCoordsList.addAll(coordAll(singleFeature.geometry()));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This will result in extra Lists creates (one per feature).
We could have a helper method that would add to existing list

private static List<Point>  addCoordAll(@NonNull List<Point> pointList, @NonNull Feature feature)

and

public static List<Point> coordAll(@NonNull Feature feature) {
    return addCoordAll(new ArrayList<Point>, @NonNull Feature feature);
}

Copy link
Contributor

@osana osana left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We want to avoid having ArrayLists created. To do so we need to have "shadow" methods for almost all public coordAll() methods.
You can keep the same name for the method. The only difference will be that the method does not create an ArrayList but instead addes points from passed in Feature or Geometry to the passed in List

I think the code snippets in the review will be sefl explanatory.

@@ -142,6 +145,81 @@ private TurfMeta() {
return coords;
}

/**
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here is one way to approach the implementation and to avoid unneeded ArrayList() creattion.
We have public coorAll methods for all Geometries. We can add private versions that take List as an extra parameter. See the example below:

public static List<Point> coordAll(@NonNull Polygon polygon, boolean excludeWrapCoord) {
     return coordAll(new ArrayList<Point>(), polygon, excludeWrapCoord);
  }

  private  static List<Point> coordAll(@NonNull List<Point> coords,
                                       @NonNull Polygon polygon, boolean excludeWrapCoord) {
    int wrapShrink = excludeWrapCoord ? 1 : 0;

    for (int i = 0; i < polygon.coordinates().size(); i++) {
      for (int j = 0; j < polygon.coordinates().get(i).size() - wrapShrink; j++) {
        coords.add(polygon.coordinates().get(i).get(j));
      }
    }
    return coords;
  }

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ahhhh, I see now. Got it.

The changes above would break semver, correct? Or to preserve, could we just deprecate the current public static List<Point> coordAll(@NonNull Polygon polygon, boolean excludeWrapCoord) { and create a new coordAll(@NonNull Polygon polygon, boolean excludeWrapCoord) as you've done above?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We are actually not breaking semver-major as only private static methods are added. It is a semver-minor change as new APIs are added.

public static List<Point> coordAll(@NonNull FeatureCollection featureCollection) {
List<Point> finalCoordsList = new ArrayList<>();
for (Feature singleFeature : featureCollection.features()) {
finalCoordsList.addAll(addCoordAll(finalCoordsList, singleFeature));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It should be just:
addCoordAll(finalCoordsList, singleFeature);

* @return a {@code List} made up of {@link Point}s
* @since 4.7.0
*/
private static List<Point> coordAllFromSingleGeometry(@NonNull Geometry geometry) {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Add `List to the list of parameters, then it will look something like:

  private static List<Point> coordAll(@NonNull List<Point> pointList, @NonNull Geometry geometry) {
    if (geometry instanceof Point) {
      pointList.add((Point) geometry);

    } else if (geometry instanceof MultiPoint) {
      pointList.addAll(((MultiPoint)geometry).coordinates());

    } else if (geometry instanceof LineString) {
      pointList.addAll(((LineString)geometry).coordinates());

    } else if (geometry instanceof MultiLineString) {
      coordAll(pointList, (MultiLineString) geometry);

    } else if (geometry instanceof Polygon) {
      coordAll(pointList, (Polygon) geometry);

    } else if (geometry instanceof MultiPolygon) {
      coordAll(pointList, (MultiPolygon) geometry);

    } else if (geometry instanceof GeometryCollection) {
      // recursive
      for (Geometry singleGeometry : ((GeometryCollection) geometry).geometries()) {
        coordAll(pointList, singleGeometry);
      }
    }
    return pointList;
  }

}

private static List<Point> addCoordAll(@NonNull List<Point> pointList, @NonNull Feature feature) {
pointList.addAll(coordAllFromSingleGeometry(feature.geometry()));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should be :
return coordAll(pointList, feature.geometry());

@langsmith langsmith force-pushed the ls-adding-coordAll-for-Feature-and-FeatureCollection branch 2 times, most recently from d157b26 to a907321 Compare April 24, 2019 20:28
@langsmith
Copy link
Author

Ok @osana , just pushed two commits that address your feedback above. Mainly added the code that you suggested above. I had to add a @NonNull boolean excludeWrapCoord parameter to the Feature & FeatureCollection methods because the boolean is needed in

 else if (geometry instanceof Polygon) {
      coordAll(pointList, (Polygon) geometry, excludeWrapCoord);

    } else if (geometry instanceof MultiPolygon) {
      coordAll(pointList, (MultiPolygon) geometry, excludeWrapCoord);

    } else if (geometry instanceof GeometryCollection) {
      // recursive
      for (Geometry singleGeometry : ((GeometryCollection) geometry).geometries()) {
        coordAllFromSingleGeometry(pointList, singleGeometry, excludeWrapCoord);
      }
    }

Anyways. Let me know how things look now.

Copy link
Contributor

@osana osana left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looking good. I think it is almost there.
Newly added methods should have @NonNull return annotation as do the public methods.

@@ -142,6 +145,81 @@ private TurfMeta() {
return coords;
}

/**
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We are actually not breaking semver-major as only private static methods are added. It is a semver-minor change as new APIs are added.

@langsmith langsmith force-pushed the ls-adding-coordAll-for-Feature-and-FeatureCollection branch 3 times, most recently from 369c041 to 64dbdce Compare April 24, 2019 22:53
@langsmith
Copy link
Author

Ok @osana . Just pushed and rebased. Added the @NonNull annotations where needed and also adjusted mentions of @since 4.7.0 to @since 4.8.0.

Copy link
Contributor

@osana osana left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks like one @nonnull got missed

return finalCoordsList;
}

private static List<Point> addCoordAll(@NonNull List<Point> pointList, @NonNull Feature feature,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@langsmith langsmith force-pushed the ls-adding-coordAll-for-Feature-and-FeatureCollection branch from 64dbdce to f6cf92b Compare April 25, 2019 06:21
@langsmith langsmith merged commit c0be138 into master Apr 25, 2019
@langsmith langsmith deleted the ls-adding-coordAll-for-Feature-and-FeatureCollection branch April 25, 2019 06:34
@osana osana added this to the v4.8.0 milestone May 7, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants