给定一个输入文件,包含40亿个非负整数。产生一个不在该文件中的整数。内存限制:1GB…

给定一个输入文件,包含40亿个非负整数。产生一个不在该文件中的整数。内存限制:1GB…

大家好,又见面了,我是全栈君。

/**
 * 功能:给定一个输入文件,包含40亿个非负整数。产生一个不在该文件中的整数。内存限制:1GB
 * 进阶:内存限制10MB。

 */

 

 

[java] view plain copy

 

  1. /** 
  2.  * 思路: 
  3.  *  
  4.  * 1)创建包含40个亿个比特的位向量。 
  5.  *     位向量(BV,bit vector)其实就是数组,利用整数(或另一种数据类型)数组紧凑地储存布尔值。每个整数可存储一串32比特或布尔值。 
  6.  * 2)将BV的所有元素初始化为0. 
  7.  * 3)扫描文件中的所有数字(num),并调用BV.set(num,1)。 
  8.  * 4)接着,再次从索引0开始扫描BV。 
  9.  * 5)返回第一个值为0的索引。 
  10.  *  
  11.  *  
  12.  * 值的确定: 
  13.  * 1)2^32——>40亿个不同的整数,一个整数4个字节。 
  14.  * 2)2^30字节——>1GB——>2^33bit——>80亿比特位。每一位映射一个不同的整数,可以存储之多80亿个不同的整数。 
  15.  */  
  16. long numberOfInts=((long)Integer.MAX_VALUE)+1;  
  17. byte[] bitfield=new byte[(int) (numberOfInts/8)];  
  18.   
  19. public void findOpenNumber() throws FileNotFoundException{  
  20.     Scanner in=new Scanner(new FileReader(“f:\\file.txt”));  
  21.       
  22.     while(in.hasNext()){  
  23.         int n=in.nextInt();  
  24.         /* 
  25.          *  使用OR操作符设置一个字节的第n位,找出bitfield中相对应的数字。 
  26.          * (例如,10(十进制)将对应于字节数组中索引2的第2位) 
  27.          */  
  28.         bitfield[n/8]=(byte) (1<<(n%8));  
  29.     }  
  30.       
  31.     for(int i=0;i<bitfield.length;i++){  
  32.         for(int j=0;j<8;j++){  
  33.             /* 
  34.              * 取回每个字节的各个比特。当发现某个比特为0时,即找到相对应的值。 
  35.              */  
  36.             if((bitfield[i]&(1<<j))==0){  
  37.                 System.out.println(i*8+j);  
  38.                 return;  
  39.             }  
  40.         }  
  41.     }  
  42. }  

 

 

进阶:10MB

 

[java] view plain copy

 

  1. /** 
  2.  * 思路:对数据集进行两次扫描,就可以找出不在文件中的整数。可以将全部整数划分为同等大小的区块。 
  3.  * 第一次扫描数组:确定每个数组的元素个数。 
  4.  * 第二次扫描位向量:确定该范围内少的数字。 
  5.  *  
  6.  * bitSize::第一次扫描时每个块范围的大小。 
  7.  * blockNum:第一次扫描时块的个数。 
  8.  *  
  9.  * 值的确定: 
  10.  * 1)10MB——>2^23Byte。一个整数4个字节,因此,最多包含2^21个元素的数组。 
  11.  * 2)bitSize=(2^32/blockNum)<=2^21,所以,blockNum>=2^11。 
  12.  * 2^11<=bitSize<=2^26。 
  13.  * 在这些条件下,挑选出越靠中间的值,那么,在任何时候所诉的内存就越少。 
  14.  */  
  15.   
  16. int bitSize=1048576;  
  17. int blockNum=4096;  
  18.   
  19. byte[] bitfield2=new byte[bitSize/8];  
  20. int[] blocks=new int[blockNum];  
  21.   
  22. public void findOpenNumber2() throws FileNotFoundException{  
  23.     Scanner in=new Scanner(new FileReader(“f:\\file.txt”));  
  24.       
  25.     int starting=-1;  
  26.     while(in.hasNext()){  
  27.         int n=in.nextInt();  
  28.         blocks[n/bitfield2.length*8]++;  
  29.     }  
  30.       
  31.     for(int i=0;i<blocks.length;i++){  
  32.         /* 
  33.          * 若小于,则说明该块中至少少了一个数字 
  34.          */  
  35.         if(blocks[i]<bitfield2.length*8){  
  36.             starting=i*bitfield2.length*8;  
  37.             break;  
  38.         }  
  39.     }  
  40.       
  41.     in =new Scanner(new FileReader(“f:\\file.txt”));  
  42.     while(in.hasNext()){  
  43.         int n=in.nextInt();  
  44.         if(n>=starting&&n<starting+bitfield2.length*8){  
  45.             bitfield2[(n-starting)/8]=(byte) (1<<((n-starting)%8));  
  46.         }  
  47.     }  
  48.       
  49.     for(int i=0;i<bitfield2.length;i++){  
  50.         for(int j=0;j<8;j++){  
  51.             /* 
  52.              * 取回每个字节的各个比特。当发现某个比特为0时,即找到相对应的值。 
  53.              */  
  54.             if((bitfield2[i]&(1<<j))==0){  
  55.                 System.out.println(i*8+j+starting);  
  56.                 return;  
  57.             }  
  58.         }  
  59.     }  
  60.       

转载于:https://my.oschina.net/u/2822116/blog/792607

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/108766.html原文链接:https://javaforall.net

(0)
全栈程序员-站长的头像全栈程序员-站长


相关推荐

  • pytest重试_pytest的conftest

    pytest重试_pytest的conftest安装:pip3installpytest-rerunfailures重新运行所有失败用例要重新运行所有测试失败的用例,请使用–reruns命令行选项,并指定要运行测试的最大次数:$py

    2022年7月30日
    6
  • 两数之和c语言实现[通俗易懂]

    两数之和c语言实现[通俗易懂]int*twoSum(int*nums,intnumsSize,inttarget,int*returnSize){inti=0,j=0;*returnSize=2;int*a=(int*)malloc(sizeof(int)*2);for(i=0;i<numsSize;i++)…

    2022年6月13日
    29
  • C语言的seekg函数,C++ seekg函数用法详解[通俗易懂]

    C语言的seekg函数,C++ seekg函数用法详解[通俗易懂]很多时候用户可能会这样操作,打开一个文件,处理其中的所有数据,然后将文件倒回到开头,再次对它进行处理,但是这可能有点不同。例如,用户可能会要求程序在数据库中搜索某种类型的所有记录,当这些记录被找到时,用户又可能希望在数据库中搜索其他类型的所有记录。文件流类提供了许多不同的成员函数,可以用来在文件中移动。其中的一个方法如下:seekg(offset,place);这个输入流类的成员函数的名字se…

    2022年4月29日
    177
  • leetcode-84柱状图中最大的矩形(单调栈)「建议收藏」

    leetcode-84柱状图中最大的矩形(单调栈)「建议收藏」原题链接给定 n 个非负整数,用来表示柱状图中各个柱子的高度。每个柱子彼此相邻,且宽度为 1 。求在该柱状图中,能够勾勒出来的矩形的最大面积。以上是柱状图的示例,其中每个柱子的宽度为 1,给定的高度为 [2,1,5,6,2,3]。图中阴影部分为所能勾勒出的最大矩形面积,其面积为 10 个单位。示例:输入: [2,1,5,6,2,3]输出: 10题解对于每一个长方体,找出左边比他小的第一个长方体和右边比他小的第一个长方体,然后遍历求结即可class Solution {public

    2022年8月8日
    3
  • tomcat自定义类加载器_开发者不可以自定义类加载器

    tomcat自定义类加载器_开发者不可以自定义类加载器tomcat自定义类加载器

    2022年9月5日
    2
  • goland 激活3月最新在线激活

    goland 激活3月最新在线激活,https://javaforall.net/100143.html。详细ieda激活码不妨到全栈程序员必看教程网一起来了解一下吧!

    2022年3月15日
    45

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号