Chinaunix首页 | 论坛 | 博客
  • 博客访问: 4440667
  • 博文数量: 1214
  • 博客积分: 13195
  • 博客等级: 上将
  • 技术积分: 9105
  • 用 户 组: 普通用户
  • 注册时间: 2007-01-19 14:41
个人简介

C++,python,热爱算法和机器学习

文章分类

全部博文(1214)

文章存档

2021年(13)

2020年(49)

2019年(14)

2018年(27)

2017年(69)

2016年(100)

2015年(106)

2014年(240)

2013年(5)

2012年(193)

2011年(155)

2010年(93)

2009年(62)

2008年(51)

2007年(37)

分类:

2011-03-06 22:12:09

1-1000放在含有1001个元素的数组中,只有唯一的一个元素值重复,其它均只出现一次。每个数组元素只能访问一次,设计一个算法,将它找出来;不用辅助存储空间,能否设计一个算法实现?
发起文章:算法题,求高手. 作者: 莫贝特(MBetter) 
算法改进:利用异或的特性解决,找出重复数的问题,应该是目前最优算法。  作者:Ivony...

莫贝特给出的算法是:将所有数加起来,减去1+2+...+1000的和
Ivony给出的算法是:  
将所有的数全部异或,得到的结果与1^2^3^...^1000的结果进行异或,得到的结果就是重复数
两位算法的时间复杂度都是: 2n (莫贝特的算法可以用高斯算法简化)

莫贝特的代码C#:
  1. static void Main(string[] args)
  2. {
  3.     int[] list = new int[1001];

  4.     for (int i = 1; i < 1001; i++)
  5.         list[i - 1] = i;

  6.     Random random = new Random();
  7.     list[1000] = random.Next(1, 1000);

  8.     int sum1 = 0;
  9.     int sum2 = 0;

  10.     foreach (int i in list)
  11.         sum1 = sum1 + i;
  12.     for (int i = 1; i < 1001; i++)
  13.         sum2 = sum2 + i;

  14.     Console.WriteLine("重复的数字是:"+(sum1 - sum2).ToString());
  15.     Console.Read();
  16. }
鹤冲天的代码C#,消除了莫贝特代码存在溢出的可能
  1. public static int GetRepeated2(int[] array)
  2. {
  3.     int temp = 0;
  4.     for (int i = 0; i < array.Length; i++)
  5.         temp += array[i] - i ;
  6.     return temp;
  7. }
我根据异或方法写的代码C:
  1. /* calculate 0^1^2^3^...^N
  2.  * the theory is based on 0~3, 4~7, ...
  3.  * every four numbers' XOR return 0 */
  4. uint64_t multiple_exclusive_or(int num)
  5. {
  6.     switch (num & 0x3) {
  7.     case 0:
  8.         /* 0^num */
  9.         return num;
  10.     case 1:
  11.         return (num-1) ^ num;
  12.     case 2:
  13.         return (num-2) ^ (num-1) ^ num;
  14.     case 3:
  15.         return 0;
  16.     }
  17. }

  18. /* (T^n)^T = (T^T)^n = 0^n = n */
  19. int get_repeated(int *array, int len, int num)
  20. {
  21.     int i, result = 0;
  22.     for (i = 0; i < len; ++i) {
  23.         result ^= array[i];
  24.     }
  25.     result ^= (int) multiple_exclusive_or(num);
  26.     return result;
  27. }
有关异或相关的详细证明见Ivony的博客和回复。当然也可以自己尝试证明。

阅读(907) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~