2017-07-14 13 views
1

我有一个整数列表:l = [1,2,3,4]生成列表随机指标不包括一个特定的指数

对于此列表中,我需要随机选择一个不同元素,并在其上执行一些操作中的每个元素:

for i in range(len(l)): 
    idx = # a random index which is NOT equal to i 
    # do something with the element at idx 

我还是很新的Python和不能确定是否有办法做到这一点,而不诉诸一个循环,我产生一个随机指数,如果随机数仅停止循环不等于i。任何建议将不胜感激。

+0

你会发现在这里帮助:https://stackoverflow.com/questions/25200220/generate-a-random-derangement-of-a-list – WNG

回答

4

这样如何:生成 0N - 1之间的随机数(N是所述列表中的在这种情况下的长度),然后添加一个至数如果是等于或大于i更大。

这样,所有上述i推出的数字移位 “一补”:

 0  i   N 
before ***************** 
after ******* ********** 

或者,在一个单一的线,你可以产生 i + 1之间的数字。和N + i,并将该数字模N,在列表结束后有效地​​将其包裹:

idx = random.randrange(i + 1, len(l) + i) % len(l) 

     0  i   N 
before   ***************** 
after ******* ********** 

1)这里的含义包括下限和不包括上限,使用randrange

+0

是的,你@tobias_k,这正是我正在寻找的。一旦SO允许我,我会尽快接受它。 – RobertJoseph

+0

为什么不只是 idx = idx + 1 if idx == i else idx? – Alexey

+1

@Alexey你必须移动所有“高级”idx,否则'i + 1'的机会是两倍,并且'len(l)-1'永远不会滚动。看我的编辑。但是,如果idx == i else idx',你可以做'idx = len(l)-1。 –

-1
import random 

l = [1, 2, 3, 4] 

for x in l: 
    new_el = random.choice(l) 
    while new_el == x: 
     new_el = random.choice(l) 
    print new_el 
+0

也就是说_exactly_我在我的问题@Alexey中描述。我正在寻找其他的东西。我希望NumPy等能够做到这一点。 – RobertJoseph

1
l=[1,2,3,4,5] 
import random as rd 
def remove_index(list,index): 
    res=list[:] 
    res.pop(index) 
    return res 

for i in range(len(l)): 
    print rd.choice(remove_index(l,i)) 
+0

你想在每次迭代中做一个_full copy_的列表?如果我的清单是数百万件物品,会怎么样? – RobertJoseph

+0

我猜这有点低效。我其实是python的新手,所以我把它当作python语法的练习。 –

+0

是的,看看tobias_k的解决方案。它需要额外的内存并且只需要一个额外的比较。 – RobertJoseph

0

numpy方法:

import numpy as np 

l = np.array([1,2,3,4]) 
for i in range(len(l)): 
    idx = random.choice(np.where(l != l[i])[0]) 
    # do stuff with idx 
    print(i, idx) 

输出(表示折射率差) :

0 1 
1 2 
2 3 
3 1 
+0

如果列表中包含重复的元素(并且假设可以选取相同的元素,只要它位于不同的位置) –

+1

@tobias_k,没有人提到关于*重复元素*,OP就不同索引。为什么要写关于*重复元素*? – RomanPerekhrest

+1

没有人提到重复的元素,但这并不意味着他们不是一个问题。 OP询问除当​​前索引以外的随机索引,而您的代码产生的随机索引不是任何具有当前元素或其副本的索引。 –

0

另一种方法:

size = len(l) 
idxl = [random.choice([j for j in range(size) if j != i]) for i in range(size)] 

for idx in idxl: 
    # do something with the element at idx 
相关问题