1

我的一个客户想为他的物品使用一个唯一的代码(长篇故事......),他问我一个解决方案。该代码将由 4 部分组成,其中第一部分是发送商品的邮政编码,第二部分是供应商注册号,第三部分是发送商品的年份,最后一部分是三除法字母数字唯一字符。

如您所见,前三个部分是静态字段,同一年同一发件人永远不会改变。所以我们可以说最后一部分是那一年的标识符部分。这部分是 3 位字母数字,表示从 000 开始,以 ZZZ 结束。

问题是我的客户出于某些合理的原因,希望这部分不是连续的。例如,这不是他想要的:

06450-05-2012-000

06450-05-2012-001

06450-05-2012-002

...

06450-05-2012-ZZY

06450-05-2012-ZZZ

最后一部分应该随机产生,如:

06450-05-2012-A17

06450-05-2012-0BF

06450-05-2012-002

...

06450-05-2012-T7W

06450-05-2012-22C

但它也应该是非重复的。因此,一旦生成了可能的 id,就应该从选择池中丢弃该可能性。

我正在寻找一种有效的方法来做到这一点。

  1. 如果我只记录选定的可能性并对照它们检查新创建的可能性,那么在最坏的情况下,它总是会继续产生已经选择的可能性,尤其是在接近尾声时。
  2. 如果我一次创建所有可能性并将它们记录在表或文件中,则每次创建项目后可能需要一段时间,因为它会查找未选择的记录。顺便说一句,26 个字母 + 10 个数字意味着 46.656 种可能的组合,并且有可能添加第 4 格,这意味着 1.679.616 种可能的组合。

有没有更有效的方法可以推荐?我将使用 C# 进行编码,使用 MS SQL 进行数据库。

4

3 回答 3

4

如果您希望为每个 zip-supplier-year 元组创建远远少于36^3条目,您可能应该为最后一个字段选择一个随机值,然后检查它是否存在,如果存在则重复。

即使您创建了最大可能条目数的一半,新条目的预期值仍然只有一个失败。假设您的数据库是根据整体标识符编制索引的,那么付出的代价并不是太大。

也就是说,如果您希望使用除少数可能的标识符之外的所有标识符,那么您可能应该提前创建所有可能的记录。这听起来可能成本很高,但内存中存储未使用记录的每个空间最终都会存储一条真实记录。

我希望第一种情况更有可能,但如果不是,或者如果两者有其他组合,请添加更多信息的评论,我会修改我的答案。

于 2012-12-30T22:08:05.920 回答
4

我认为选项取决于将要使用的代码数量:

  1. 如果您希望在一年内使用其中的大部分,那么最好预先生成。如果做得对,查找应该非常快。无论如何,您的数据库中每年将有 1.679.616 个项目,因此您必须正确地做这些事情。

    另一方面,您期望使用它们中的大多数是否很好?如果突然出现比预期更多的项目,它可能会让您没有代码。

  2. 如果您希望只使用少量,那么随机+存在检查可能是一种方法,但是目前还不清楚最好的数量应该是多少(我很确定可以计算出来)。

于 2012-12-30T22:08:23.070 回答
4

如果它不必是随机的,您也许可以简单地选择一个固定但“不可预测”的加数,它与26 + 10 == 36 == 2²·3². 2这意味着,只需选择一个固定加数,该加数既不也可整除3

然后在每次需要新的序列号时,继续将此固定编号添加到您之前的序列号中。这当然是模46656(或1679616)完成的。

数学保证您不会两次获得相同的数字(在没有更多“免费”数字之前)。

作为补充,您可以使用它,const int addend = 26075因为它是5modulo 6

于 2012-12-30T22:30:35.773 回答