From e0fc38c23d196ce4d086480bbe09f2639f74c1a1 Mon Sep 17 00:00:00 2001 From: Lene Preuss Date: Tue, 12 Oct 2021 18:16:54 +0200 Subject: [PATCH] Improve decoding performance by converting string to char[] only once instead of repeatedly Signed-off-by: Lene Preuss --- .gitignore | 1 + .../flexpolyline/PolylineEncoderDecoder.java | 25 ++++++++++++------- 2 files changed, 17 insertions(+), 9 deletions(-) diff --git a/.gitignore b/.gitignore index 8a53128..1af892b 100644 --- a/.gitignore +++ b/.gitignore @@ -10,3 +10,4 @@ obj/ .vs *.user +*.class diff --git a/java/src/com/here/flexpolyline/PolylineEncoderDecoder.java b/java/src/com/here/flexpolyline/PolylineEncoderDecoder.java index ba064d7..dc8ef5f 100644 --- a/java/src/com/here/flexpolyline/PolylineEncoderDecoder.java +++ b/java/src/com/here/flexpolyline/PolylineEncoderDecoder.java @@ -109,7 +109,7 @@ public static final List decode(String encoded) { public static ThirdDimension getThirdDimension(String encoded) { AtomicInteger index = new AtomicInteger(0); AtomicLong header = new AtomicLong(0); - Decoder.decodeHeaderFromString(encoded, index, header); + Decoder.decodeHeaderFromString(encoded.toCharArray(), index, header); return ThirdDimension.fromNum((header.get() >> 4) & 7); } @@ -186,7 +186,7 @@ private String getEncoded() { */ private static class Decoder { - private final String encoded; + private final char[] encoded; private final AtomicInteger index; private final Converter latConveter; private final Converter lngConveter; @@ -198,7 +198,7 @@ private static class Decoder { public Decoder(String encoded) { - this.encoded = encoded; + this.encoded = encoded.toCharArray(); this.index = new AtomicInteger(0); decodeHeader(); this.latConveter = new Converter(precision); @@ -219,18 +219,18 @@ private void decodeHeader() { thirdDimPrecision = (int) ((header.get() >> 3) & 15); } - private static void decodeHeaderFromString(String encoded, AtomicInteger index, AtomicLong header) { + private static void decodeHeaderFromString(char[] encoded, AtomicInteger index, AtomicLong header) { AtomicLong value = new AtomicLong(0); // Decode the header version - if(!Converter.decodeUnsignedVarint(encoded.toCharArray(), index, value)) { + if(!Converter.decodeUnsignedVarint(encoded, index, value)) { throw new IllegalArgumentException("Invalid encoding"); } if (value.get() != FORMAT_VERSION) { throw new IllegalArgumentException("Invalid format version"); } // Decode the polyline header - if(!Converter.decodeUnsignedVarint(encoded.toCharArray(), index, value)) { + if(!Converter.decodeUnsignedVarint(encoded, index, value)) { throw new IllegalArgumentException("Invalid encoding"); } header.set(value.get()); @@ -240,7 +240,7 @@ private static void decodeHeaderFromString(String encoded, AtomicInteger index, private boolean decodeOne(AtomicReference lat, AtomicReference lng, AtomicReference z) { - if (index.get() == encoded.length()) { + if (index.get() == encoded.length) { return false; } if (!latConveter.decodeValue(encoded, index, lat)) { @@ -347,11 +347,11 @@ private static boolean decodeUnsignedVarint(char[] encoded, } //Decode single coordinate (say lat|lng|z) starting at index - boolean decodeValue(String encoded, + boolean decodeValue(char[] encoded, AtomicInteger index, AtomicReference coordinate) { AtomicLong delta = new AtomicLong(); - if (!decodeUnsignedVarint(encoded.toCharArray(), index, delta)) { + if (!decodeUnsignedVarint(encoded, index, delta)) { return false; } if ((delta.get() & 1) != 0) { @@ -362,6 +362,13 @@ boolean decodeValue(String encoded, coordinate.set(((double)lastValue / multiplier)); return true; } + + // Overloaded version for backwards compatibility + boolean decodeValue(String encoded, + AtomicInteger index, + AtomicReference coordinate) { + return decodeValue(encoded.toCharArray(), index, coordinate); + } } /**