最小可用id
题目:在非负数组(乱序)中找到最小的可分配的id(从1开始编号),数据量10000000。
题目解读:在一个不重复的乱序的自然数组中找到最小的缺失的那个数,比如1,2,3,6,4,5,8,11。那么最小可用id就为7。
代码:
import java.util.Arrays; /**
* 解决最小可用id问题
*/
public class MinFreeId { public static void main(String[] args) { // int[]arr = {1,5,3,2,6,7,10,9,4}; // 最开始小数据测试
int []arr = new int[1000*1000];
for (int i = 0; i < arr.length; i++) {
// if(i==900000) 那解法一运行时间就太长了
if (i==90000) {
arr[i] = arr.length+10;
}else {
arr[i] = i+1;
}
}
long now = System.currentTimeMillis();
System.out.println(find1(arr));
System.out.println("解法一消耗的时间:"+(System.currentTimeMillis()-now)+"ms"); now = System.currentTimeMillis();
System.out.println(find2(arr));
System.out.println("解法二消耗的时间:"+(System.currentTimeMillis()-now)+"ms"); now = System.currentTimeMillis();
System.out.println(find3(arr));
System.out.println("解法三消耗的时间:"+(System.currentTimeMillis()-now)+"ms"); now = System.currentTimeMillis();
System.out.println(find4(arr,0,arr.length-1));
System.out.println("解法四消耗的时间:"+(System.currentTimeMillis()-now)+"ms"); } // O(n^2) 暴力解法:从1开始依次探测每个自然数是否在数组中
static int find1(int[]arr){
int i = 1;
while(true){
for (int j = 0; j < arr.length;) {
if (arr[j]==i) {
i++;
j = 0;
continue;
}else {
j++;
}
}
return i;
}
} // O(nlgn)
static int find2(int[]arr){
Arrays.sort(arr); // O(nlgn) 后续扫描时间O(N) 相比之下 取O(nlgn) 所以时间复杂度为O(nlgn)
int i = 0;
while(i<arr.length){
if (i+1!=arr[i]) { // 不存在的最小自然数
return i+1;
}
i++;
}
return i+1;
} /**
* 改进1:用辅助空间
* 有点类似计数排序 O(N)但是浪费空间
*/
static int find3(int[]arr){
int n = arr.length;
int []helper = new int[n+1];
for (int i = 0; i < n; i++) { // O(N)
if (arr[i]<n+1) {
helper[arr[i]] = 1; // 辅助空间的下标也是有用的
}
}
for (int i = 1; i <= n; i++) { // O(N) if (helper[i] == 0) {
return i;
}
}
return n+1;
} /**
* // O(N)
* 改进2:分区,递归
* 问题可转化为:n的正数的数组A,如果存在小于n的数不在数组中,必然存在大于n的数组中,否则数组排列恰好为1到n
*/ private static int find4(int[] arr, int l, int r) {
if (l>r) {
return l+1;
}
int midIndex = l+((r-l)>>1); // 中间下标
int q = SelectK.selectK(arr, l, r, midIndex-l+1); // 调用查找第k大的元素的方法
int t = midIndex + 1; // 期望值
if (q==t) { // 左侧紧密
return find4(arr,midIndex+1,r);
}else { // 左侧稀疏
return find4(arr, l, midIndex-1);
}
}
}
结果:

结论:根据每个解法所消耗的时间即可得出哪个解法的效率更高。所以在数据量较大的情况下最好选用O(lgn)和O(N)级别的算法,O(nlgn)次之。
最小可用id的更多相关文章
- mysql查询表中最小可用id值
今天在看实验室的项目时,碰到的一个问题,.先把sql语句扔出来 // 这条语句在id没有1时,不能得到正确的查询结果. select min(id+1) from oslist c where not ...
- SQL-42 删除emp_no重复的记录,只保留最小的id对应的记录
题目描述 删除emp_no重复的记录,只保留最小的id对应的记录.CREATE TABLE IF NOT EXISTS titles_test (id int(11) not null primary ...
- SQL server 存储过程 C#调用Windows CMD命令并返回输出结果 Mysql删除重复数据保留最小的id C# 取字符串中间文本 取字符串左边 取字符串右边 C# JSON格式数据高级用法
create proc insertLog@Title nvarchar(50),@Contents nvarchar(max),@UserId int,@CreateTime datetimeasi ...
- 最小可用 Spring MVC 配置
[最小可用 Spring MVC 配置] 1.导入有概率用到的JAR包, -> pom.xml 的更佳实践 - 1.0 <- <project xmlns="http:// ...
- 相同name,取最小的id的值,mysql根据相同字段 更新其它字段
id name info1 a 1232 a 2353 a 1244 b 125 b 987相同name,取最小的id的值id name info1 a 1232 a 1233 a 1234 b 12 ...
- mysql删除表中重复数据,只保留一个最小的id的记录
语句: delete from table1 where id not in (select minid from (select min(id) as minid from table1 group ...
- Mysql删除重复数据保留最小的id
在网上查找删除重复数据保留id最小的数据,方法如下: DELETE FROM people WHERE peopleName IN ( SELECT peopleName FROM people GR ...
- Salesforce 生成测试可用 Id
在写 Test Class 的时候,有时候需要一批有 Id 的数据或者把 Id 作为参数等情况,在数据关系比较复杂的情况下去造真实数据有些麻烦,于是找到这样一个可以生成 Id 的方法可以用来辅助测试! ...
- 从0移植uboot(三) _编译最小可用uboot
前两篇介绍了uboot-2013.01的配置原理以及大体的运行流程,本文将讨论如何对uboot源码进行配置,将一个可用的uboot烧录到SD卡中. 定制自己的core board 市面上能买到的开发板 ...
随机推荐
- Nginx 中利用 Lua 脚本做访问控制
使用场景 需要在后端服务之前做访问控制,或没有后端服务的场景,如静态文件. 实验环境 Ubuntu 14.04 Nginx 1.4.6 安装 Lua 运行环境 sudo apt-get install ...
- vue -- style使用scss样式报错
1.报错信息 2.解决方案(vue-li默认没有scss-loader,scss-loader)安装以下依赖 (1) npm install node-sass --save (2)npm insta ...
- Android开发PreferenceActivity 用法的代码
将开发过程中常用的一些内容做个收藏,下面资料是关于Android开发PreferenceActivity 用法的内容,希望对大伙有一些用处.public class Setting extends P ...
- C# 实现 Snowflake算法生成唯一性Id
参考地址:https://blog.csdn.net/w200221626/article/details/52064976 /// <summary> /// 动态生产有规律的ID // ...
- DevExpress控件库 开发使用经验总结2 DevExpress汉化之WinForm开发模式汉化
2015-01-24 DevExpress控件库默认安装后,使用的本地资源为英文.Developer Express .NET产品都有本地化资源,比如按钮属性,控件属性描述,菜单项,确认和错误的信息等 ...
- systemd-unit
参考: systemd unit 中文手册
- C语言作业06--结构体&文件
1.本章学习总结 1.1 思维导图 1.2学习体会 在本周的学习中,我们学习了关于结构体和文件的内容.定义结构体可以使代码整个练习更加紧密,非常实用,当我们需要在对一个个体的不同属性调用时可以更加系统 ...
- Unreal 4 error 记录
1.打包出来的exe,黑屏 这种最大的可能是在“地图&模式中”将 Default Maps设置为自己的map,注意这里分为Editor Startup Map和Game Default Map ...
- Java 扫描实现 Ioc 动态注入,过滤器根据访问url调用自定义注解标记的类及其方法
扫描实现 Ioc 动态注入 参考: http://www.private-blog.com/2017/11/16/java-%e6%89%ab%e6%8f%8f%e5%ae%9e%e7%8e%b0-i ...
- 30分钟,让你彻底明白Promise原理
前言 前一阵子记录了promise的一些常规用法,这篇文章再深入一个层次,来分析分析promise的这种规则机制是如何实现的.ps:本文适合已经对promise的用法有所了解的人阅读,如果对其用法还不 ...