UUID to unique integer id?
Answering the How can I have a unique application wide Integer:
If it needs to be unique even after restarts or if you application is clustered you may use a Database sequence.
If it just needs to be unique during the runtime use a static AtomicInteger.
EDIT (example added):
public class Sequence {
private static final AtomicInteger counter = new AtomicInteger();
public static int nextValue() {
return counter.getAndIncrement();
}
}
Usage:
int nextValue = Sequence.nextValue();
This is thread safe (different threads will always receive distinct values, and no values will be "lost")
You are going to have a problem since the UUID is 128 bits and the int is only 32bit. You'll either have to accept the risk of collisions and try to fudge it to a smaller space (hashCode
is probably a good way to do that) or find an alternative (use the UUID
directly, map to a BigInteger
- difficult to tell without knowing why)
We had a requirement to convert all our UUIDs into serial numbers. Finally, we tested and used the next algorithm:
Get CRC64 of uuid(16 bytes) using the ECMA polynomial 0xC96C5795D7870F42. Do not use ISO polynomial because it could cause a lot of collisions for some UUID generation algorithms.
Now we have crc64(8 bytes). Take the first N bytes(in our case 5 in yours it will be 4 bytes for int and all bytes for int64)
We tested this method and it works well for several million UUIDs.
Our additional step: convert 5 bytes number into a number with base 36 and finally we have SN: 4YD3SOJB.
A UUID is a 16-Byte number (128 bit). You can't crunch it into an int
(32 bit) while preserving it's uniqueness.
Mathematically spoken: 296 UUIDs will share the same Java-int
-size hash value (which is ... a lot ;) )
A way out - some real life UUID often have a rather static part. So in isolated scenarios, the real unique portion of UUIDs may be less then 32 bit.