刷题复习(二)数组-双指针
刷题复习(二)数组-双指针
https://labuladong.gitee.io/algo/di-ling-zh-bfe1b/shuang-zhi-fa4bd/
1、删除有序数组中的重复项
慢指针用于统计不重复项,快指针用于不停前进对比是否有新的不重复项,有的话进行替换
class Solution {
public int removeDuplicates(int[] nums) {
int i = 0, j = i + 1;
while (i <= nums.length - 1 && j <= nums.length - 1) {
if (nums[i] != nums[j]) {
i++;
nums[i] = nums[j];
}
j++;
}
return i + 1;
}
}
2、删除排序链表中的重复元素
和上面的数组比较类似
/**
* Definition for singly-linked list.
* public class ListNode {
* int val;
* ListNode next;
* ListNode() {}
* ListNode(int val) { this.val = val; }
* ListNode(int val, ListNode next) { this.val = val; this.next = next; }
* }
*/
class Solution {
public ListNode deleteDuplicates(ListNode head) {
if(head == null) return head;
ListNode fast = head;
ListNode slow = head;
while (fast != null) {
if (fast.val != slow.val) {
slow.next =fast;
slow =slow.next;
}
fast = fast.next;
}
slow.next = null;
return head;
}
}
//leetcode submit region end(Prohibit modification and deletion)
3、移除元素
一样是快慢指针变化
如果 fast
遇到值为 val
的元素,则直接跳过,否则就赋值给 slow
指针,并让 slow
前进一步。
class Solution {
public int removeElement(int[] nums, int val) {
int slow = 0;
int fast = 0;
while (fast < nums.length) {
if (nums[fast] != val) {
nums[slow]=nums[fast];
slow++;
}
fast++;
}
return slow;
}
}
4、移动零
同样的道理,多了一个slow以外的的数据需要变成0
class Solution {
public void moveZeroes(int[] nums) {
int slow =0;
int fast =0;
while(fast < nums.length){
if(nums[fast] != 0){
nums[slow] = nums[fast];
slow++;
}
fast ++;
}
while(slow<nums.length){
nums[slow++] =0;
}
}
}
二分查找框架
int binarySearch(int[] nums, int target) {
// 一左一右两个指针相向而行
int left = 0, right = nums.length - 1;
while(left <= right) {
int mid = (right + left) / 2;
if(nums[mid] == target)
return mid;
else if (nums[mid] < target)
left = mid + 1;
else if (nums[mid] > target)
right = mid - 1;
}
return -1;
}
5、两数之和 II
同样是快慢窗口,比较简单
class Solution {
public int[] twoSum(int[] numbers, int target) {
int left = 0, right = numbers.length - 1;
while(left < right){
if(numbers[left] + numbers[right] == target){
return new int[]{left+1,right+1};
}else if(numbers[left] + numbers[right] < target){
left++;
}else{
right--;
}
}
return new int[]{-1,-1};
}
}
6、反转字符串
class Solution {
public void reverseString(char[] s) {
int left = 0, right = s.length - 1;
char temp = 0;
while (left <= right) {
temp = s[left];
s[left] = s[right];
s[right] = temp;
left++;
right--;
}
}
}
回文字符串判断
boolean isPalindrome(String s) {
// 一左一右两个指针相向而行
int left = 0, right = s.length() - 1;
while (left < right) {
if (s.charAt(left) != s.charAt(right)) {
return false;
}
left++;
right--;
}
return true;
}
7、最长回文子串
回文串除了左右对比靠近的方式,还有以一个或者俩个字符左右扩散的方式进行判断
class Solution {
public String longestPalindrome(String s) {
int left = 0;
String res = "";
while (left < s.length()) {
String max1 = help(s, left, left);
String max2 = help(s, left, left + 1);
res = res.length() > max1.length() ? res : max1;
res = res.length() > max2.length() ? res : max2;
left++;
}
return res;
}
private String help(String s, int left, int right) {
while (left >= 0 && right < s.length() && s.charAt(left) == s.charAt(right)) {
left--;
right++;
}
return s.substring(left + 1, right);
}
}