2010-08-03 41 views
1

这就是我如何在1到6之间生成一个唯一的no,并从可绘制文件夹中获取适当的图像。如何拥有唯一的随机数?

Random rand = new Random(); 
// n = the number of images, that start at idx 1 
rndInt = rand.nextInt(6) + 1; 
String imgName = "card" + rndInt; 
int id = getResources().getIdentifier(imgName, "drawable", getPackageName()); 
imgView.setImageResource(id); 

我想要的是,我必须调用这个方法7次,每次这个方法应该返回一个唯一的随机号码。所以没有一个已经选择的数字会再次出现。

+1

如果只有6个可能的值,你打算怎么获得7个唯一的号码? – 2010-08-03 11:14:44

+10

“唯一”和“随机”是互斥的。你不能拥有两个。 – 2010-08-03 11:18:13

+0

@丹代尔先生我的坏。我把它改为7. @greg D ..伙计,PLZ C被接受的answr..that代码创建了一个独特的和赎金没有。 – iscavengers 2010-08-03 12:05:47

回答

37

这种问题的常见方法是创建一个列表,其中包含每个可能的值并将其拖动(使用Collections.shuffle)。每次你需要一个值时,你从列表中消耗一个项目。这将确保您不会多次使用相同的值,但仍允许随机订购。

+0

它看起来像你用这个来洗牌。加载所有的卡片,然后洗牌会不会更好?该方法与此答案类似。 – 2010-08-03 12:03:21

+3

+1比接受的答案好得多。我想知道你的代码是否已被接受。 – MAK 2010-08-03 12:26:36

-4

创建一个你已经获得的可能性的静态列表。

static ArrayList<int> listIdontWantAnymore = new ArrayList<int>(); 

int NextRandomNumber() { 
    Random random = new Random(); 
    int myRandomInt; 

    do { 
     myRandomInt = random.NextInt(6) + 1; 
    } while(listIdontWantAnymore.Contains(myRandomInt)); 

    listIdontWantAnymore.Add(myRandomInt); 

    // now your 'myRandomInt' is what you want it to be. 
    return myRandomInt; 
} 
+4

我认为像这样的解决方案应该有失效保护系统来避免死锁。它可能会坏的;) – monoceres 2010-08-03 11:27:30

+0

这是完美的,人.. dat wat我waz寻找,现在我能够创建一个独特的随机数 非常感谢。 – iscavengers 2010-08-03 12:04:27

+6

@ shishir.bobby:不,那并不完美。那真是太可怕了。请不要使用这个“解决方案”。 – 2010-08-03 12:20:51

8

下面是一个使用Dan Dyer建议的方法创建随机排列的示例类。它确保每个.next()调用都给出一个新的数字,直到构造函数中给出的数字为止。之后,它会环绕并再次提供相同的序列。 这对洗牌播放列表很有用。

import java.util.ArrayList; 
import java.util.Collections; 
import java.util.List; 

public class RandomPermutation{ 
    private List<Integer> list; 
    private int index; 

    /** 
    * Create a random permutation the sequence of numbers 0, 1, ... , n - 1. 
    * @param n Range specifier, must be positive 
    */ 
    public RandomPermutation(int n) { 
     if (n <= 1) { 
      throw new IllegalArgumentException(
        "Positive number expected, got: " + n); 
     } 
     list = new ArrayList<Integer>(); 
     newList(n); 
    } 

    /** 
    * Creates a new list 
    */ 
    public void newList(int n) { 
     index = -1; 
     list.clear(); 
     for (int i = 0; i < n; i++) { 
      list.add(i); 
     } 
     Collections.shuffle(list); 
    } 

    /** 
    * Retrieve the next integer in sequence. 
    */ 
    public int next() { 
     index = (index + 1) % list.size(); 
     return list.get(index); 
    } 
} 

Btw。不要使用Snake使用的方法。 这不仅仅是因为一旦所有的数字都被使用,它会冻结。这可以修复。 由于越来越多的数字在listIdontWantAnymore中,问题在于程序运行速度越来越慢。只有6个数字不是问题,但如果范围很大,它可能会导致相当大的减速。考虑选择10000个数字。在选择了9900个数字后,有1%的机会击中一个好数字。后9990号有创下了相当数量等

这里的0.1%的几率是你如何使用类的一个示例:

static RandomPermutation randomPerm = new RandomPermutation(7) 

int NextRandomNumber() { 
    return randomPerm.next() + 1; 
} 
+0

谢谢zeriab,我实现了你的方法,它的工作f9。 可以告诉我一件事, 像你一定要看到一个计时器,倒数计时器,显示值从10到0,在视图中可见。 我如何显示随机数字不断更改我的看法。 再次感谢队友 – iscavengers 2010-08-06 11:33:28

1

您的特定用例,这应该做的诀窍。

Random rand = new Random(); 
// n = the number of images 
List<String> imgNames = new ArrayList<String>(n); 
for (int i = 0; i < n; i++) { 
    imgNames.add("card" + (i + 1)) 
} 
while (!imageNames.isEmpty()) { 
    String imgName = imgNames.remove(rand.next(imageNames.size()); 
    int id = getResources().getIdentifier(imgName, "drawable", getPackageName()); 
    imgView.setImageResource(id); 
} 

请注意,这不能很好地扩展,因为n变大。对于ArrayListLinkedList,删除操作是O(n)。但是对于成百上千的n,与加载和显示图像相比,这可能是微不足道的。

此外,正如评论指出的“独特的随机数”是一个矛盾的术语。你在后面是从1n的一组数字的随机置换。我的解决方案在没有明确的“洗牌”步骤的情况下为您提供了这一点,这对您的使用情况已足够。

+0

我会说这很清楚,“独特的随机数”意味着同一个样本不应该被挑选超过一次。 在附注上:LinkedList上的removeFirst()操作是O(1)。 – Zeriab 2010-08-03 13:00:41

+0

@Zeriab - *“LinkedList上的removeFirst()操作是O(1)”*。这有什么关系?该算法不使用该方法。 – 2010-08-03 13:35:21

+0

@Zeriab - “独特的随机数”对你来说可能很清楚,但从数学的角度来看这是无稽之谈。有点像讨论允许重复的集合。 – 2010-08-03 13:39:36

1

生成包含您将使用的每个数字的数字列表。 (这很好,因为我们正在谈论一个小范围,其中“N”是“某处少于一千个”)

当您选择一个数字时,请选择一个介于0和sizeof(list)之间的随机索引,该数字成为该列表的索引。

删除该列表索引并返回该数字。

(这是一个锻炼的读者,以确定什么样的“名单”是适当的在这里。)

2

这里是最简单的代码来做到这一点,并存储到一个数组中没有任何重复:

Random rand = new Random(); 
int[] ar; 
ar = new int[5]; 

int random = 0; 
int [] result_arr=new int[5]; 
boolean flag=false; 

for(int i=0;i<5;i++) 
{ 
    ar[i]=0; 

    do{ 
     random =rand.nextInt(10); 
     flag=false; 
     for(int j=0;j<i;j++) 
     { 
      if(ar[j]==random) 
      flag=true; 
     } 
     if(!flag) 
     { 
      ar[i]=random; 
      break; 
     } 
    } 
    while(true) ; 
} 

这将在阵列中创建独特的数字