C#算法之向一个集合中插入随机不重复的100个数

一道非常经典的C#笔试题:

需求:请使用C#将一个长度为100的int数组,插入1-100的随机数,不能重复,要求遍历次数最少。

1.最简单的办法

 1 var rd = new Random();
 2 List<int> list = new List<int>();
 3 var num = 0;
 4 while (list.Count<100)
 5 {
 6     num = rd.Next(1, 101);
 7     if (!list.Contains(num))
 8     {
 9         list.Add(num);
10     }
11 }

这种办法无需解释。

2.进阶

var rd = new Random();
var hs = new HashSet<int>();
while (hs.Count < 100)
{
    hs.Add(rd.Next(1, 101));
}

这种方案较上个方案差别不大,HashSet对于重复数据只保存一次,少了个if判断。

3.高级

List<int> list1 = new List<int>(), list2 = new List<int>();
for (int i = 1; i < 101; i++)
{
    list1.Add(i);
}

var rd = new Random();
while (list2.Count < 100)
{
    var index = rd.Next(0, list1.Count - 1);
    list2.Add(list1[index]);
    list1.RemoveAt(index);
}

此方案一共遍历200次,初始化遍历100次,重新赋值再遍历100次,并且数字是随机不重复的。

每遍历一次,list1就会删除一个元素,即使产生的随机数据相同,但每次对于list1的索引对应的值是不同的,能保证数字唯一性。

 1 using System;
 2 using System.Collections.Generic;
 3 
 4 namespace Random100
 5 {
 6     class Program
 7     {
 8         static void Main(string[] args)
 9         {
10             Test1();
11             Console.WriteLine("------------------华丽的分割线--------------------");
12             Test2();
13             Console.WriteLine("------------------华丽的分割线--------------------");
14             Test3();
15             Console.ReadKey();
16         }
17 
18         static void Test1()
19         {
20             var rd = new Random();
21             List<int> list = new List<int>();
22             var count = 0;
23             while (list.Count < 100)
24             {
25                 var num = rd.Next(1, 101);
26                 if (!list.Contains(num))
27                 {
28                     list.Add(num);
29                 }
30                 count++;
31             }
32             foreach (var i in list)
33             {
34                 Console.Write(i + "	");
35             }
36             Console.WriteLine("Test1共遍历了{0}次.", count);
37         }
38 
39         static void Test2()
40         {
41             var rd = new Random();
42             var hs = new HashSet<int>();
43             var count = 0;
44             while (hs.Count < 100)
45             {
46                 hs.Add(rd.Next(1, 101));
47                 count++;
48             }
49             foreach (var i in hs)
50             {
51                 Console.Write(i + "	");
52             }
53             Console.WriteLine("Test2共遍历了{0}次.", count);
54         }
55 
56         static void Test3()
57         {
58             List<int> list1 = new List<int>(), list2 = new List<int>();
59             var count = 0;
60             for (int i = 1; i < 101; i++)
61             {
62                 list1.Add(i);
63                 count++;
64             }
65 
66             var rd = new Random();
67             while (list2.Count < 100)
68             {
69                 var index = rd.Next(0, list1.Count - 1);
70                 list2.Add(list1[index]);
71                 list1.RemoveAt(index);
72                 count++;
73             }
74             foreach (var i in list2)
75             {
76                 Console.Write(i + "	");
77             }
78             Console.WriteLine("Test3共遍历了{0}次.", count);
79         }
80     }
81 }
全部代码

我们来看看这三种方案分别遍历了多少次:

方案一515次,方案二529次,方案一、方案二差不多,全靠人品,方案三始终都是200次,要少得qq多,但方案三有个bug,最后一个数据始终都是100。

如果修复这个bug,或者你有更好的办法,请分享下,不胜感激!

如果觉得对你有帮助,请点个赞,谢谢!

不足与错误之处,敬请批评指正!

原文地址:https://www.cnblogs.com/xiaoafei1991/p/4470074.html