在 Marklogic (XQuery) 中使用时间戳生成非重复随机数?
Generate non-repeating random number using timestamp in Marklogic (XQuery)?
我想生成带有时间戳的非重复随机数。它的可能代码是什么?
我试过使用 sem:uuid-string() 函数,但它生成了 36 个很长的字符。
我建议看一下 ml-unique 库。它提供了 3 种在 MarkLogic 中生成唯一 id 的不同方法,并解释了每种方法的优缺点。也许其中之一符合您的需求,或者您可以复制代码,并根据需要进行调整。
请注意,仅时间戳不足以保证唯一性,尤其是在一个请求中生成多个 ID 或并行处理数据时。
顺便说一句,uuid字符串的长度使得冲突的可能性很小。
HTH!
无法生成非重复随机数并使结果适合有限大小。如果 36 字节太大,则进一步限制了理论最大值。服务器本身使用 64 位随机数(有效 xdmp:random)作为唯一 ID。尝试在冲突概率方面做得更好是徒劳的——无论您使用什么 URI 或使用多长时间,内部引用都将创建为 64 位随机数或哈希值。推荐的方法不会产生有效的冲突 URI,其概率比服务器本身给出任何大小的非冲突 URI 的概率低。由于伪随机数算法的微妙之处,最有可能尝试更复杂的 'random' URI 生成会导致更糟糕的结果。
下面的代码生成(任意高概率)10 个不同的随机数。 for 循环的每次迭代都会将新生成的随机数插入 MarkLogic 数据库。当已经生成了 10 个不同的数字时,将抛出异常 error((), 'BREAK')。
xquery version "1.0-ml";
xdmp:document-insert("/doc/random.xml",<root><a>{xdmp:random(100)}</a></root>);
try {
for $i in (1 to 200) (:200 can be replace with larger number to reduce probability that 10 different random numbers will never be selected.:)
return xdmp:invoke-function( function() as item()?
{ let $myrandom:= xdmp:random(100), $last:= count(doc("/doc/random.xml")/root/*)
return
if ($last lt 10) then (
if (doc("/doc/random.xml")/root/a/text() = $myrandom) then () else (xdmp:node-insert-after(doc("/doc/random.xml")/root/a[last()], <a>{$myrandom}</a>)))
else (if ($last eq 10) then (error((), 'BREAK')) else ())},
<options xmlns="xdmp:eval">
<transaction-mode>update</transaction-mode>
<transaction-mode>update-auto-commit</transaction-mode>
</options>)}
catch ($ex) {
if ($ex/error:code eq 'BREAK') then ("10 different random numbers were generated") else xdmp:rethrow() };
我想生成带有时间戳的非重复随机数。它的可能代码是什么?
我试过使用 sem:uuid-string() 函数,但它生成了 36 个很长的字符。
我建议看一下 ml-unique 库。它提供了 3 种在 MarkLogic 中生成唯一 id 的不同方法,并解释了每种方法的优缺点。也许其中之一符合您的需求,或者您可以复制代码,并根据需要进行调整。
请注意,仅时间戳不足以保证唯一性,尤其是在一个请求中生成多个 ID 或并行处理数据时。
顺便说一句,uuid字符串的长度使得冲突的可能性很小。
HTH!
无法生成非重复随机数并使结果适合有限大小。如果 36 字节太大,则进一步限制了理论最大值。服务器本身使用 64 位随机数(有效 xdmp:random)作为唯一 ID。尝试在冲突概率方面做得更好是徒劳的——无论您使用什么 URI 或使用多长时间,内部引用都将创建为 64 位随机数或哈希值。推荐的方法不会产生有效的冲突 URI,其概率比服务器本身给出任何大小的非冲突 URI 的概率低。由于伪随机数算法的微妙之处,最有可能尝试更复杂的 'random' URI 生成会导致更糟糕的结果。
下面的代码生成(任意高概率)10 个不同的随机数。 for 循环的每次迭代都会将新生成的随机数插入 MarkLogic 数据库。当已经生成了 10 个不同的数字时,将抛出异常 error((), 'BREAK')。
xquery version "1.0-ml";
xdmp:document-insert("/doc/random.xml",<root><a>{xdmp:random(100)}</a></root>);
try {
for $i in (1 to 200) (:200 can be replace with larger number to reduce probability that 10 different random numbers will never be selected.:)
return xdmp:invoke-function( function() as item()?
{ let $myrandom:= xdmp:random(100), $last:= count(doc("/doc/random.xml")/root/*)
return
if ($last lt 10) then (
if (doc("/doc/random.xml")/root/a/text() = $myrandom) then () else (xdmp:node-insert-after(doc("/doc/random.xml")/root/a[last()], <a>{$myrandom}</a>)))
else (if ($last eq 10) then (error((), 'BREAK')) else ())},
<options xmlns="xdmp:eval">
<transaction-mode>update</transaction-mode>
<transaction-mode>update-auto-commit</transaction-mode>
</options>)}
catch ($ex) {
if ($ex/error:code eq 'BREAK') then ("10 different random numbers were generated") else xdmp:rethrow() };