Efficient method to generate UUID String in JAVA (

2019-01-29 20:24发布

I would like an efficient utility to generate unique sequences of bytes. UUID is a good candidate but UUID.randomUUID().toString() generates stuff like 44e128a5-ac7a-4c9a-be4c-224b6bf81b20 which is good as long as you don't need to transmit it over HTTP, in which case the dashes need to be removed.

I'm looking for an efficient way to generate a random strings, only from alphanumeric characters (no dashes or any other special symbols).

8条回答
迷人小祖宗
2楼-- · 2019-01-29 21:03

Dashes don't need to be removed from HTTP request as you can see in URL of this thread. But if you want to prepare well-formed URL without dependency on data you should use URLEncoder.encode( String data, String encoding ) instead of changing standard form of you data. For UUID string representation dashes is normal.

查看更多
再贱就再见
3楼-- · 2019-01-29 21:03

I am amazed to see so many string replace ideas of UUID. How about this:

UUID temp = UUID.randomUUID();
String uuidString = Long.toHexString(temp.getMostSignificantBits())
     + Long.toHexString(temp.getLeastSignificantBits());

This is the fasted way of doing it since the whole toString() of UUID is already more expensive not to mention the regular expression which has to be parsed and executed or the replacing with empty string.

查看更多
干净又极端
4楼-- · 2019-01-29 21:03

A simple solution is

UUID.randomUUID().toString().replace("-", "")

(Like the existing solutions, only that it avoids the String#replaceAll call. Regular expression replacement is not required here, so String#replace feels more natural, though technically it still is implemented with regular expressions. Given that the generation of the UUID is more costly than the replacement, there should not be a significant difference in runtime.)

Using the UUID class is probably fast enough for most scenarios, though I would expect that some specialized hand-written variant, which does not need the postprocessing, to be faster. Anyway, the bottleneck of the overall computation will normally be the random number generator. In case of the UUID class, it uses SecureRandom.

Which random number generator to use is also a trade-off that depends on the application. If it is security-sensitive, SecureRandom is, in general, the recommendation. Otherwise, ThreadLocalRandom is an alternative (faster than SecureRandom or the old Random, but not cryptographically secure).

查看更多
等我变得足够好
5楼-- · 2019-01-29 21:11

I use org.apache.commons.codec.binary.Base64 to convert a UUID into a url-safe unique string that is 22 characters in length and has the same uniqueness as UUID.

I posted my code on Storing UUID as base64 String

查看更多
Bombasti
6楼-- · 2019-01-29 21:14

Ended up writing something of my own based on UUID.java implementation. Note that I'm not generating a UUID, instead just a random 32 bytes hex string in the most efficient way I could think of.

Implementation

import java.security.SecureRandom;
import java.util.UUID;

public class RandomUtil {
    // Maxim: Copied from UUID implementation :)
    private static volatile SecureRandom numberGenerator = null;
    private static final long MSB = 0x8000000000000000L;

    public static String unique() {
        SecureRandom ng = numberGenerator;
        if (ng == null) {
            numberGenerator = ng = new SecureRandom();
        }

        return Long.toHexString(MSB | ng.nextLong()) + Long.toHexString(MSB | ng.nextLong());
    }       
}

Usage

RandomUtil.unique()

Tests

Some of the inputs I've tested to make sure it's working:

public static void main(String[] args) {
    System.out.println(UUID.randomUUID().toString());
    System.out.println(RandomUtil.unique());

    System.out.println();
    System.out.println(Long.toHexString(0x8000000000000000L |21));
    System.out.println(Long.toBinaryString(0x8000000000000000L |21));
    System.out.println(Long.toHexString(Long.MAX_VALUE + 1));
}
查看更多
一纸荒年 Trace。
7楼-- · 2019-01-29 21:15

This does it:

public static void main(String[] args) {
    final String uuid = UUID.randomUUID().toString().replace("-", "");
    System.out.println("uuid = " + uuid);
}
查看更多
登录 后发表回答