Given a sorted array, remove the duplicates
in-place such that each element appear only
once and
return the new length.
Do not allocate extra space for another array, you must do this by
modifying the input array in-place with
O(1) extra memory.
Example:
Given
nums
= [1,1,2],
Your function should return length = 2, with the first two elements of
nums
being 1 and 2 respectively.
It doesn't matter what you leave beyond the new length.
一開始也想到了雙指針 first指向重複的第一個元素 second從first開始找第一個不重複元素 這樣出現了兩個問題
1.我是不是需要把first後面的重複元素都替換掉
比如 1,2,2,2,2,3,4
如果只覆蓋掉第一個重複元素 變爲
1,2,3,2,2,4
那麼怎麼判斷後面的2是重複元素呢 還需要set維護
2.如果需要覆蓋掉後面所有重複元素 那麼對於每一個重複元素 都需要在其後面遍歷尋找到非重複元素 感覺時間複雜度O(n^2)
像下面這樣
public int removeDuplicates(int[] nums) {
int index = 0, count = 0;
while (index < nums.length) {
int pre = nums[index];
if (++index == nums.length) return ++count;
if (nums[index] == pre) {
int start = index;
int end = start;
while (end<nums.length && nums[end]==pre) {
end++;
}
if (end == nums.length) return ++count;
for (int i=start; i<end; i++) {
nums[i] = nums[end];
}
}
count++;
}
return count;
}
實際上是不需要這樣的
1.不需要知道這個元素和前面的所有元素是否重複 只要和後面的不相等 替換就可以了 注意是sorted array
比如 1,2,2,2,2,3,4
如果只覆蓋掉第一個重複元素 變爲
1,2,3,2,2,4
start指向3後面的2 之後發現4和2不相等 用4覆蓋掉2就可以了
2.實際上不是每個元素都需要向後遍歷 只要end到達末尾 就結束了 所以時間複雜度O(n)
下面的solution更加簡潔
public int removeDuplicates(int[] nums) {
if (nums.length == 0) return 0;
int i = 0;
for (int j = 1; j < nums.length; j++) {
if (nums[j] != nums[i]) {
i++;
nums[i] = nums[j];
}
}
return i + 1;
}