题目要求:
算法分析:
本题是荷兰国旗问题。
我的思路最开始也是双指针,只不过是比较指针所指向值的大小再进行变化。即循环判断条件为nums[i]
和nums[j]
的大小再做出相应的判断,但是这种方法在测试的过程中[2,0,1]这个数组没有通过,而且要求判断的条件为nums[i]==nums[j]
时还需要附加判断条件:值为0,1还是2.较为繁琐,由于条件的控制不能完全涵盖每一种情况因此不能采用这种比较指针所指向值的大小再进行变化。
————————————————————————————————————
在变换思路之后,依旧使用双指针(也可以理解为三指针),指向不再用来比较大小,而是用作边界,此时的双指针分别是:
low:指向0所在的右边界,不包含边界;
high:指向2所在的左边界,不包含边界;
i:作为索引,指向的数据和0,1,2比较。
这样我们可以进行如下判断和分区:
当nums[i]==0
时,和nums[low]
交换
当nums[i]==2
时,和nums[high]
交换
当nums[i]==1
时,只需将i做增量。
这种方法还需注意结束条件,不是low与high作比较,而应该是i与high作比较,因为low永远是0的右边界(开)而high永远是2的左边界(开)。
是否有等于号也不是固定的,在于high作为左边界的开or闭。如果编码时设置为开则需要等于号,即在nums[i]与nums[high]指向相同值时还需判断,否则可能会漏掉最后一个0。
源代码:
class Solution {
public void sortColors(int[] nums) {
int low=0, high=nums.length-1;
int temp;
int i=0;
while(i<=high){
if(nums[i]==0){
temp = nums[i];
nums[i] = nums[low];
nums[low] = temp;
low++;
i++;
}
else if(nums[i]==1){
i++;
}
else{
temp = nums[i];
nums[i] = nums[high];
nums[high] = temp;
high--;
}
}
}
}
其他解法:
(来自leetcode官方题解,原网页链接)