RFR: 8316681: Rewrite URLEncoder.encode to use small reusable buffers [v6]

温绍锦 duke at openjdk.org
Fri Oct 6 18:45:20 UTC 2023


On Fri, 22 Sep 2023 08:53:07 GMT, Claes Redestad <redestad at openjdk.org> wrote:

>> `URLEncoder` currently appends chars that needs encoding into a `java.io.CharArrayWriter`, converts that to a `String`, uses `String::getBytes` to get the encoded bytes and then appends these bytes in a escaped manner to the output stream. This is somewhat inefficient.
>> 
>> This PR replaces the `CharArrayWriter` with a reusable `CharBuffer` + `ByteBuffer` pair. This allows us to encode to the output `StringBuilder` in small chunks, with greatly reduced allocation as a result.
>> 
>> The exact size of the buffers is an open question, but generally it seems that a tiny buffer wins by virtue of allocating less, and that the per chunk overheads are relatively small.
>
> Claes Redestad has updated the pull request incrementally with one additional commit since the last revision:
> 
>   Update src/java.base/share/classes/java/net/URLEncoder.java
>   
>   Co-authored-by: ExE Boss <3889017+ExE-Boss at users.noreply.github.com>

The improvement is about 3% to 13% under microbench. The baseline is based on BitSet table lookup. In real scenarios, the performance of the new version that does not use BitSet should be better.

Performance numbers running on MacBook M1 Pro: 

-Benchmark                         (encodeChars)  (maxLength)  (unchanged)  Mode  Cnt  Score   Error  Units (baseline)
-URLEncodeDecode.testEncodeLatin1              6         1024            0  avgt   15  2.244 ? 0.290  ms/op
-URLEncodeDecode.testEncodeLatin1              6         1024           75  avgt   15  0.956 ? 0.074  ms/op
-URLEncodeDecode.testEncodeLatin1              6         1024          100  avgt   15  0.400 ? 0.006  ms/op

+Benchmark                         (encodeChars)  (maxLength)  (unchanged)  Mode  Cnt  Score    Error  Units (optimized)
+URLEncodeDecode.testEncodeLatin1              6         1024            0  avgt   15  2.057 ?  0.016  ms/op (+9.10)
+URLEncodeDecode.testEncodeLatin1              6         1024           75  avgt   15  0.842 ?  0.002  ms/op (+13.54)
+URLEncodeDecode.testEncodeLatin1              6         1024          100  avgt   15  0.385 ?  0.001  ms/op (+3.90)

-------------

PR Comment: https://git.openjdk.org/jdk/pull/15865#issuecomment-1751244288


More information about the net-dev mailing list