【问题标题】:Given an array of integers {1..n}, and a date, how do I randomly choose a unique element based on the date?给定一个整数数组 {1..n} 和一个日期,如何根据日期随机选择一个唯一元素?
【发布时间】:2012-04-28 14:15:50
【问题描述】:

我只是概括了标题中的问题。

我要解决的实际问题是这样的。我正在制作一个网站,我需要填写网站的“随机文章”部分。这篇随机文章必须显示一整天。因此,我正在尝试提出一种算法,该算法会根据今天的日期从数据库中选择 1 个元素。

我有一个包含大约 100,000 篇文章的数据库。

假设今天的日期是2012-04-28。我也许可以总结数字来选择文章的 ID。在这种情况下,2012+4+28 = 2044。但这是2012-04-282013-04-27 会显示同一篇文章的问题。

我也不希望算法在附近的两天内两次选择同一篇文章。我希望选择是独一无二的。 (理想情况下,我希望它是一个生成函数,涵盖连续 100,000 天的全部 100,000 篇文章。)

我想不出另一种方法来根据日期选择文章。有什么想法吗?

【问题讨论】:

  • 需要随机选择文章,还是可以顺序选择文章?
  • @AdamLiss 最好是随机选择。

标签: datetime random generator choice


【解决方案1】:

您可以将日期连接起来,使 2012-04-28 变为 20120428

我知道这个数字大于您数据库中的文章数量,但是您可以减去开始显示这些文章的日期,然后显示文章 20120428-20120428=0 今天和文章 20120429-20120428=1 明天。

【讨论】:

  • 非常好的解决方案,类似于@Adam Liss 的。但是,正如我在上面的评论中提到的,它会按顺序选择文章。我宁愿让他们随机选择。你能想出一种方法把这个顺序算法变成随机算法吗?
  • 我记得关于场论、Z_p 之类的东西,整数模素数,关于生成器的东西,以及如何将它提升到素数产生 Z_p 中的所有元素。我想知道我是否可以在这里使用这个数论的东西。不过我自己也不是很擅长。
【解决方案2】:

如果您只是计算网站上线后的天数,那么您的问题归结为将序列 1、2、3...n 映射到随机序列.

一个简单的方法是创建一个数组,其中包含从 1 到 n 随机顺序的数字。然后,对于每一天 i,您可以使用 i<sup>th</sup> 元素。

例如,假设 n = 4 并且您已经像这样随机填充数组:

a[0] = 3
a[1] = 1
a[2] = 4
a[3] = 2

该数组具有随机序列 3、1、4、2,因此随着时间的推移,您将选择第 3 条,然后选择第 1 条,然后选择第 4 条,最后选择第 2 条。

【讨论】:

  • 这是一个不错的解决方案。我没有想到。但是它会按顺序选择文章。我宁愿让他们随机选择。
  • @bodacydo 这就是为什么你要用随机顺序的序列填充数组:这会创建一个随机序列。然后,当您遍历数组时,您将继续前进到序列中的下一个随机数。我会澄清答案。
  • 我记得关于场论、Z_p 之类的东西,整数模素数,关于生成器的东西,以及如何将它提升到素数产生 Z_p 中的所有元素。我想知道我是否可以在这里使用这个数论的东西。不过我自己也不是很擅长。
  • 我还可以生成一个包含 100,000 个数字的列表,对列表进行置换,然后将您建议的算法应用于列表,每天选择 1 个元素。但是,这需要我在某处以随机顺序存储 100,000 个 ID。 100,000 个 ID 是 400,000 字节 == 400KB 的数据!不多,但我还是要把它放在某个地方,要么是新表,要么是外部文件。
  • 我刚刚有了一个很好的想法——我可以找到一个周期大约为 100,000 的伪随机数生成器(或尝试自己构建一个),然后总是在使用它之前使用 my_seed 播种它,然后给出第一天n,生成nth 随机数。但是我发现这种方法存在一个主要问题,要达到第 100,000 个元素,我必须调用我的函数 100,000 次,这很令人沮丧。
【解决方案3】:

我会以不同的方式处理这个问题。我会为每篇文章分配一个唯一编号,并从 [1..number of article] 范围内选择一个随机数。这让您克服了生成有效随机日期的困难。

分配编号的一种方法是按发布日期对文章进行排序,然后分配最旧的文章 1,依此类推。如果这些文章存储在数据库中,那么数据库的主键很可能适合您的需求。

顺便说一句,文章的编号方式并不重要。文章集甚至不需要为这个想法进行排序(例如,如果它们存储在无序哈希表中)。

在极少数情况下,您可能需要多次调用生成器函数,它会为不再可用的文章(可能隐藏或删除)返回一个数字。但是,假设不可用文章的数量很少,这种情况不会经常发生,也不会成为性能问题。

【讨论】:

  • 经审查,这与@Adam Liss 的类似,但在数字到文章的映射中不涉及日期。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-07-25
  • 1970-01-01
  • 1970-01-01
  • 2013-01-31
  • 1970-01-01
相关资源
最近更新 更多