简体   繁体   English

从不同长度的多个列表中获取随机整数的更有效和通用的方法

[英]More efficient and general way of getting a random integer from multiple lists of different lengths

What I want is to be able to have mutable lists of mutable length and draw a random number from these lists.我想要的是能够拥有可变长度的可变列表并从这些列表中抽取一个随机数。 The trick is that these lists are different sizes so if a list is smaller than the others a number from it should not come up as often as from the other bigger lists.诀窍是这些列表的大小不同,所以如果一个列表比其他列表小,那么它中的数字不应该像其他更大的列表那样经常出现。

Here's what I have now:这是我现在所拥有的:

 import random

 a = 1
 b = 11
 c = 111
 d = 1111
 e = 11111
 f = 111111
 g = f - e
 q = (f - e) + (d - c) + (b - a)
 r = ((f - e) / q ) * g
 s = g - ((b - a) / q ) * g

 low = 1
 mid = 1
 high = 1

 i = 1
 while i < 666666:
     x = random.randint(a, b)
     y = random.randint(c, d)
     z = random.randint(e, f)
     v = random.randint(1, g)
     if v < r:
         print(z)
         high += 1
     else:
         if v > s:
             print(x)
             low += 1
         else:
             print(y)
             mid += 1
     i += 1

 print(low, mid, high)



  ...
  72027
  81188
  57 6579 660032

It works, but it's very crude and requires me to know which list is the longest, etc. Thanks.它有效,但它非常粗糙,需要我知道哪个列表最长,等等。谢谢。

Make a list of all the input lists.列出所有输入列表。 Then pick a random number from 0 to the combined length of the lists.然后从0到列表的组合长度选择一个随机数。 Then loop over the incremental lengths of the lists until you get to the one where the index points, and select the element of that list.然后遍历列表的增量长度,直到到达索引指向的位置,然后选择该列表的元素。

l1 = [1, 2, 3, 4, 5]
l2 = [10, 20, 30]
l3 = [100, 101, 105, 107, 111, 125, 130]
l4 = [200, 202, 204, 300, 303, 306, 400, 404, 408]
list_of_lists = [l1, l2, l3, l4]
index = random.randint(0, sum(len(l) for l in list_of_lists))
listnum = 0
prev_length = 0
running_length = len(list_of_lists[listnum])
while index >= running_length:
    prev_length = running_length
    listnum += 1
    running_length += len(list_of_lists[listnum])
result = list_of_lists[listnum][index - prev_length]

Just pick from the concatenaded lists, possibly without reinventing the wheel and avoiding indexing:只需从串联列表中选择,可能无需重新发明轮子并避免索引:

import itertools as it
import random as ra

l1 = [1, 2, 3, 4, 5]
l2 = [10, 20, 30]
l3 = [100, 101, 105, 107, 111, 125, 130]
l4 = [200, 202, 204, 300, 303, 306, 400, 404, 408]

res = ra.choice(list(it.chain(l1, l2, l3, l4)))
print(res)

Note: if the number of lists varies, make a list of them and pass it to chain.from_iterable注意:如果列表的数量不同,请列出它们并将其传递给chain.from_iterable

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM