题目一:
剑指 Offer 03. 数组中重复的数字https://leetcode-cn.com/problems/shu-zu-zhong-zhong-fu-de-shu-zi-lcof/
想法一:使用flag数组标记是否出现过
想法二:考虑到数字只有0~n-1,所以遍历将每个数字交换到顺序位置,当交换途中位置上数字已经正确时则为重复值
想法三:使用hashset.contains()判断唯一
代码:
//法一
class Solution {
public int findRepeatNumber(int[] nums) {
boolean[] flag= new boolean[nums.length];
for (int i = 0; i < nums.length; i++) {
if (flag[nums[i]]){
return nums[i];
}
if (!flag[nums[i]]){
flag[nums[i]]=true;
}
}
return -1;
}
}
//法二
class Solution {
public int findRepeatNumber(int[] nums) {
int i = 0;
//"遍历"数组,将数字放在0~n-1顺序应在位置
while(i < nums.length) {
//实际上是在一个位置多exchange几次,直到换来了本位置应有的数字,才顺到下一位置
if(nums[i] == i) {
i++;
continue;
}
//若已有数字在应在位置,则是重复
if(nums[nums[i]] == nums[i])
return nums[i];
//在一个位置exchange几次
int tmp=nums[i];
nums[i]=nums[tmp];
nums[tmp]=tmp;
}
//空数组返回-1
return -1;
}
}
//法三
class Solution {
public int findRepeatNumber(int[] nums) {
HashSet<Integer> set =new HashSet<>();
for(int i=0;i<nums.length;i++){
if(set.contains(nums[i]))
return nums[i];
set.add(nums[i]);
}
return -1;
}
}
结果一:
结果二:
结果三:
题目二:
代码:
//法一:遍历计数
class Solution {
public int search(int[] nums, int target) {
int count=0;
for (int i = 0; i < nums.length; i++) {
if(nums[i]==target)
count++;
}
return count;
}
}
//法二:二分法查找tar的左右边界
class Solution {
public int search(int[] nums, int target) {
return helper(nums, target) - helper(nums, target - 1);
}
int helper(int[] nums, int tar) {
//二分法查找tar数字的右侧数字的位置(该位置可能越界)
//如[5,7,7,8,8,10] 8,tar=8时返回5,tar=7时返回3
//如[1] 1,tar=1时返回1,tar=0时返回0
int i = 0, j = nums.length - 1;
while(i <= j) {
int m = (i + j) / 2;
//临界点:i==j
//二分法查找tar数字的 右侧数字 的位置
if(nums[m] <= tar)
i = m + 1;
else
j = m - 1;
}
return i;
}
}
//法二的另一种写法
class Solution {
public int search(int[] nums, int target) {
int n=nums.length;
int high=n-1;
int low=0;
int res=0;
int mid=0;
while(low<=high){
mid=(low+high)/2;
if(nums[mid]<target)
low=mid+1;
else
high=mid-1;
//low 第一个不小于target的
}
res=low;
low=mid;
high=n-1;
while(low<=high){
mid=(low+high)/2;
if(nums[mid]<=target)
low=mid+1;
else
high=mid-1;
//low 第一个大于target的
}
return low-res;
}
}
结果:
题目三:
剑指 Offer 53 - II. 0~n-1中缺失的数字https://leetcode-cn.com/problems/que-shi-de-shu-zi-lcof/
代码:
//法一:遍历
class Solution {
public int missingNumber(int[] nums) {
for (int i = 0; i < nums.length; i++) {
if(nums[i]!=i)
return i;
}
return nums.length;
}
}
//法二:二分法
class Solution {
public int missingNumber(int[] nums) {
int i = 0, j = nums.length - 1;
while(i <= j) {
int m = (i + j) / 2;
if(nums[m] == m)
i = m + 1;
else
j = m - 1;
}
return i;
}
}
结果: