剑指 Offer 03. 数组中重复的数字
解法一:HashSet
class Solution {
public int findRepeatNumber(int[] nums) {
Set<Integer> set = new HashSet<>();
for (int num : nums) {
if (!set.add(num)) {
return num;
}
}
return -1;
}
}
解法二:辅助数组(哈希桶思想)
class Solution {
public int findRepeatNumber(int[] nums) {
int[] tmp = new int[nums.length];
for (int i = 0; i < nums.length; ++i) {
tmp[nums[i]]++;
if (tmp[nums[i]] == 2) {
return nums[i];
}
}
return -1;
}
}
解法三:排序
class Solution {
public int findRepeatNumber(int[] nums) {
Arrays.sort(nums);
for (int i = 1; i < nums.length; ++i) {
if (nums[i - 1] == nums[i]) {
return nums[i];
}
}
return -1;
}
}
解法四:原地交换
class Solution {
public int findRepeatNumber4(int[] nums) {
for (int i = 0; i < nums.length; ++i) {
while (nums[i] != i) {
//遇到重复元素
if (nums[i] == nums[nums[i]]) {
return nums[i];
}
//交换
int tmp = nums[i];
nums[i] = nums[tmp];
nums[tmp] = tmp;
}
}
return -1;
}
}
剑指 Offer 53 - I. 在排序数组中查找数字 I
解法一:暴力破解
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;
}
}
解法二:HashMap
class Solution {
public int search(int[] nums, int target) {
Map<Integer, Integer> map = new HashMap<>();
for (int n : nums) {
map.put(n, map.getOrDefault(n, 0) + 1);
}
return map.get(target) == null ? 0 : map.get(target);
}
}
解法三:二分法
class Solution {
public int search(int[] nums, int target) {
int left = 0, right = nums.length - 1;
while (left <= right) {
int mid = (left + right) >> 1;
if (target < nums[mid]) {
//比mid小,在左侧
right = mid - 1;
} else if (target > nums[mid]) {
//比mid大,在右侧
left = mid + 1;
} else {
//等于mid
if (target != nums[left]) {
//left像右缩
left++;
} else if (target != nums[right]) {
//right像左缩
right--;
} else {
//说明就在这个区间内
break;
}
}
}
return right - left + 1;
}
}
剑指 Offer 53 - II. 0~n-1中缺失的数字
解法一:遍历顺序
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 left = 0, right = nums.length - 1;
while (left <= right) {
int mid = (left + right) >> 1;
if (nums[mid] != mid) {
right = mid - 1;
} else {
left = mid + 1;
}
}
return left;
}
}