Skip to content

Commit 6681658

Browse files
committed
PackedCoordinateSequence separated arrays variant
1 parent 1ce7a94 commit 6681658

File tree

3 files changed

+212
-4
lines changed

3 files changed

+212
-4
lines changed

modules/core/src/main/java/org/locationtech/jts/geom/impl/PackedCoordinateSequence.java

Lines changed: 179 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -420,6 +420,185 @@ public Envelope expandEnvelope(Envelope env)
420420
}
421421
}
422422

423+
public static class Double2 extends PackedCoordinateSequence {
424+
private static final long serialVersionUID = 5777450686367912720L;
425+
426+
double[] xy;
427+
double[] z;
428+
double[] m;
429+
430+
/**
431+
* Builds a new packed coordinate sequence
432+
*
433+
* @param coords an array of <c>double</c> values that contains the ordinate values of the sequence
434+
* @param dimension the total number of ordinates that make up a {@link Coordinate} in this sequence.
435+
* @param measures the number of measure-ordinates each {@link Coordinate} in this sequence has.
436+
*/
437+
public Double2(double[] xy, double[] z, double[] m) {
438+
super(z != null ? 3 : 2, m != null ? 1 : 0);
439+
this.xy = xy;
440+
this.z = z;
441+
this.m = m;
442+
}
443+
444+
/**
445+
* Builds a new packed coordinate sequence out of a coordinate array
446+
*
447+
* @param coordinates an array of {@link Coordinate}s
448+
* @param dimension the total number of ordinates that make up a {@link Coordinate} in this sequence.
449+
*/
450+
public Double2(Coordinate[] coordinates, int dimension) {
451+
this( coordinates, dimension, Math.max(0,dimension-3));
452+
}
453+
/**
454+
* Builds a new packed coordinate sequence out of a coordinate array
455+
*
456+
* @param coordinates an array of {@link Coordinate}s
457+
* @param dimension the total number of ordinates that make up a {@link Coordinate} in this sequence.
458+
* @param measures the number of measure-ordinates each {@link Coordinate} in this sequence has.
459+
*/
460+
public Double2(Coordinate[] coordinates, int dimension, int measures) {
461+
super(dimension,measures);
462+
if (coordinates == null)
463+
coordinates = new Coordinate[0];
464+
465+
xy = new double[coordinates.length];
466+
for (int i = 0; i < coordinates.length; i++) {
467+
xy[i * 2] = coordinates[i].x;
468+
xy[i * 2 + 1] = coordinates[i].y;
469+
if (dimension == 3)
470+
z[i] = coordinates[i].getOrdinate(2);
471+
if (measures == 1)
472+
m[i] = coordinates[i].getOrdinate(3);
473+
}
474+
}
475+
/**
476+
* Builds a new packed coordinate sequence out of a coordinate array
477+
*
478+
* @param coordinates an array of {@link Coordinate}s
479+
*/
480+
public Double2(Coordinate[] coordinates) {
481+
this(coordinates, 3, 0);
482+
}
483+
484+
/**
485+
* Builds a new empty packed coordinate sequence of a given size and dimension
486+
*
487+
* @param size the number of coordinates in this sequence
488+
* @param dimension the total number of ordinates that make up a {@link Coordinate} in this sequence.
489+
* @param measures the number of measure-ordinates each {@link Coordinate} in this sequence has.
490+
*/
491+
public Double2(int size, int dimension, int measures) {
492+
super(dimension,measures);
493+
xy = new double[size * 2];
494+
if (dimension == 3)
495+
z = new double[size];
496+
if (measures == 1)
497+
m = new double[size];
498+
}
499+
500+
/**
501+
* @see PackedCoordinateSequence#getCoordinate(int)
502+
*/
503+
public Coordinate getCoordinateInternal(int i) {
504+
double x = xy[i * 2];
505+
double y = xy[i * 2 + 1];
506+
if( dimension == 2 && measures == 0 ) {
507+
return new CoordinateXY(x,y);
508+
}
509+
else if (dimension == 3 && measures == 0) {
510+
double z = this.z[i];
511+
return new Coordinate(x,y,z);
512+
}
513+
else if (dimension == 3 && measures == 1) {
514+
double m = this.m[i];
515+
return new CoordinateXYM(x,y,m);
516+
}
517+
else if (dimension == 4) {
518+
double z = this.z[i];
519+
double m = this.m[i];
520+
return new CoordinateXYZM(x,y,z,m);
521+
}
522+
return new Coordinate(x, y);
523+
}
524+
525+
/**
526+
* Gets the underlying array containing the coordinate values.
527+
*
528+
* @return the array of coordinate values
529+
*/
530+
public double[] getRawXYCoordinates()
531+
{
532+
return xy;
533+
}
534+
535+
/**
536+
* @see CoordinateSequence#size()
537+
*/
538+
public int size() {
539+
return xy.length / 2;
540+
}
541+
542+
/**
543+
* @see java.lang.Object#clone()
544+
* @see PackedCoordinateSequence#clone()
545+
* @deprecated
546+
*/
547+
public Object clone() {
548+
return copy();
549+
}
550+
551+
/**
552+
* @see PackedCoordinateSequence#size()
553+
*/
554+
public Double2 copy() {
555+
double[] cloneXy = Arrays.copyOf(xy, xy.length);
556+
double[] cloneZ = z != null ? Arrays.copyOf(z, z.length) : null;
557+
double[] cloneM = m != null ? Arrays.copyOf(m, m.length) : null;
558+
return new Double2(cloneXy, cloneZ, cloneM);
559+
}
560+
561+
/**
562+
* @see PackedCoordinateSequence#getOrdinate(int, int)
563+
* Beware, for performance reasons the ordinate index is not checked, if
564+
* it's over dimensions you may not get an exception but a meaningless
565+
* value.
566+
*/
567+
public double getOrdinate(int index, int ordinate) {
568+
if (ordinate <= 1)
569+
return xy[index * 2 + ordinate];
570+
if (ordinate == 2)
571+
return z[index];
572+
if (ordinate == 3)
573+
return m[index];
574+
throw new RuntimeException("Ordinate must be <= 3");
575+
}
576+
577+
/**
578+
* @see PackedCoordinateSequence#setOrdinate(int, int, double)
579+
*/
580+
public void setOrdinate(int index, int ordinate, double value) {
581+
coordRef = null;
582+
if (ordinate <= 1)
583+
xy[index * 2 + ordinate] = value;
584+
if (ordinate == 2)
585+
z[index] = value;
586+
if (ordinate == 3)
587+
m[index] = value;
588+
}
589+
590+
/**
591+
* @see CoordinateSequence#expandEnvelope(Envelope)
592+
*/
593+
public Envelope expandEnvelope(Envelope env)
594+
{
595+
for (int i = 0; i < xy.length; i += 2 ) {
596+
env.expandToInclude(xy[i], xy[i + 1]);
597+
}
598+
return env;
599+
}
600+
}
601+
423602
/**
424603
* Packed coordinate sequence implementation based on floats
425604
*/

modules/core/src/main/java/org/locationtech/jts/geom/impl/PackedCoordinateSequenceFactory.java

Lines changed: 29 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,11 @@ public class PackedCoordinateSequenceFactory implements
3939
*/
4040
public static final int FLOAT = 1;
4141

42+
/**
43+
* Type code for dim/measure separated arrays of type <code>double</code>.
44+
*/
45+
public static final int DOUBLE2 = 1;
46+
4247
/**
4348
* A factory using array type {@link #DOUBLE}
4449
*/
@@ -51,6 +56,12 @@ public class PackedCoordinateSequenceFactory implements
5156
public static final PackedCoordinateSequenceFactory FLOAT_FACTORY =
5257
new PackedCoordinateSequenceFactory(FLOAT);
5358

59+
/**
60+
* A factory using array type {@link #DOUBLE2}
61+
*/
62+
public static final PackedCoordinateSequenceFactory DOUBLE2_FACTORY =
63+
new PackedCoordinateSequenceFactory(DOUBLE2);
64+
5465
private static final int DEFAULT_MEASURES = 0;
5566

5667
private static final int DEFAULT_DIMENSION = 3;
@@ -100,8 +111,10 @@ public CoordinateSequence create(Coordinate[] coordinates) {
100111
}
101112
if (type == DOUBLE) {
102113
return new PackedCoordinateSequence.Double(coordinates, dimension, measures);
103-
} else {
114+
} else if (type == FLOAT) {
104115
return new PackedCoordinateSequence.Float(coordinates, dimension, measures);
116+
} else {
117+
return new PackedCoordinateSequence.Double2(coordinates, dimension, measures);
105118
}
106119
}
107120

@@ -113,8 +126,10 @@ public CoordinateSequence create(CoordinateSequence coordSeq) {
113126
int measures = coordSeq.getMeasures();
114127
if (type == DOUBLE) {
115128
return new PackedCoordinateSequence.Double(coordSeq.toCoordinateArray(), dimension, measures);
116-
} else {
129+
} else if (type == FLOAT) {
117130
return new PackedCoordinateSequence.Float(coordSeq.toCoordinateArray(), dimension, measures);
131+
} else {
132+
return new PackedCoordinateSequence.Double2(coordSeq.toCoordinateArray(), dimension, measures);
118133
}
119134
}
120135

@@ -148,6 +163,11 @@ public CoordinateSequence create(double[] packedCoordinates, int dimension, int
148163
return new PackedCoordinateSequence.Float(packedCoordinates, dimension, measures);
149164
}
150165
}
166+
167+
public CoordinateSequence create(double[] xy, double[] z, double[] m) {
168+
return new PackedCoordinateSequence.Double2(xy, z, m);
169+
}
170+
151171
/**
152172
* Creates a packed coordinate sequence of type {@link #FLOAT}
153173
* from the provided array.
@@ -184,9 +204,12 @@ public CoordinateSequence create(int size, int dimension) {
184204
if (type == DOUBLE) {
185205
return new PackedCoordinateSequence.Double(
186206
size, dimension, Math.max(DEFAULT_MEASURES, dimension-3));
187-
} else {
207+
} else if (type == FLOAT) {
188208
return new PackedCoordinateSequence.Float(
189209
size, dimension, Math.max(DEFAULT_MEASURES, dimension-3));
210+
} else {
211+
return new PackedCoordinateSequence.Double2(
212+
size, dimension, Math.max(DEFAULT_MEASURES, dimension-3));
190213
}
191214
}
192215

@@ -196,8 +219,10 @@ public CoordinateSequence create(int size, int dimension) {
196219
public CoordinateSequence create(int size, int dimension, int measures) {
197220
if (type == DOUBLE) {
198221
return new PackedCoordinateSequence.Double(size, dimension, measures);
199-
} else {
222+
} else if (type == FLOAT) {
200223
return new PackedCoordinateSequence.Float(size, dimension, measures);
224+
} else {
225+
return new PackedCoordinateSequence.Double2(size, dimension, measures);
201226
}
202227
}
203228
}

modules/core/src/test/java/org/locationtech/jts/geom/impl/PackedCoordinateSequenceTest.java

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,10 @@ public void testDouble() {
5151
public void testFloat() {
5252
checkAll( PackedCoordinateSequenceFactory.FLOAT_FACTORY) ;
5353
}
54+
55+
public void testDouble2() {
56+
checkAll( PackedCoordinateSequenceFactory.DOUBLE2_FACTORY) ;
57+
}
5458

5559
public void checkAll(CoordinateSequenceFactory factory)
5660
{

0 commit comments

Comments
 (0)