【Leetcode27】

122 阅读1分钟

两种思路,我采用了第二种但是没有写出来

1.仍然采用双指针方式

这个方法利用的是遇到指定变量val时两个指针的递增差异

开始两指针初始位置,当j指针当前元素不为val时,将j处的元素复制给i,对于i,j重合的情况这个操作没有实质意义。之后递增i,j

当j指向的元素为val时,只递增j指针,这样得到ij指针的差异,每遇到一次val就会相差一个位置,而当j元素不为val时又会将i所指向的val元素用其它元素覆盖,保证了i及之前元素都是非val元素。

代码:

public static int removeElement(int[] nums, int val){
    //maintain two pointers, i from the front j from back
    if(nums.length==0) return 0;
    else{
        int i=0;
        for(int j=0;j<nums.length;j++){
            if(nums[j]!=val){
                nums[i]=nums[j];
                i++;
            }
        }
        return i;
    }
}

2.第二种方法可以理解为第二个指针在数组末尾

i指针依然从头检查,当元素不为val时i++ 当元素为val时,我们已知这个位置的元素需要被舍弃,虽然不知道末尾的元素是否也需要被舍弃,但是我们可以再次检查。

将末尾元素复制给i处,进行下次检查。并让末尾指针向左移动一位。

我写这里的时候问题在于同时让前后的指针移动,当指针交错的时候检查语句出现了问题。

代码:

public static int removeElement(int[] nums, int val){
    //maintain two pointers, i from the front j from back
    if(nums.length==0) return 0;
    else{
        int n= nums.length;
        int i=0;
        while (i<n){
            if(nums[i]==val){
                nums[i]=nums[n-1];
                n--;
            }
            else i++;
        }
        return i;
    }

}