这是一个短命的应用程序,没有数据库,只保留原始的>缩短内存。如果我有跟随每次调用的scala方法,生成一个值(然后用作缩短的URL),然后保存在Map(originalUrl-> shortenUrl。用redix选择42亿(Integer.MAX_VALUE)) 36.如果在多线程环境中调用,生成唯一缩短URL值的方法有任何缺点吗?
def randomUrl: String = {
Integer.toString(new Random().nextInt(Integer.MAX_VALUE), 36)
}
答案 0 :(得分:1)
你不应该有任何问题。以下一个衬垫是Scala Random构造函数。
def this() = this(new java.util.Random())
默认构造函数的OpenJDK源代码确实使用System.nanoTime(),但它不仅仅使用时间。它使用AtomicLong并调用compareAndSet(原子操作)来设置新值。 This atomic operation is thread-safe.如果该值已由另一个线程设置,它将重试另一个AtomicLong值以使您的种子唯一。
public Random() {
this(seedUniquifier() ^ System.nanoTime());
}
private static long seedUniquifier() {
// L'Ecuyer, "Tables of Linear Congruential Generators of
// Different Sizes and Good Lattice Structure", 1999
for (;;) {
long current = seedUniquifier.get();
long next = current * 181783497276652981L;
if (seedUniquifier.compareAndSet(current, next))
return next;
}
}
答案 1 :(得分:0)
非唯一性可能只是31位信息的问题。在生成大约64k个URL之后,您将会发生第一次碰撞。使用更多位。并且你不能确保你的种子与这种方法不同,所以你最好不要创建一个随机数源并分享它。
java.util.Random
是线程安全的,而Scala只是转发到Java实现,所以即使你没有为每个调用创建一个新的Random
,你也应该在线程安全性方面做得很好。 / p>