zoukankan      html  css  js  c++  java
  • LeetCode——75. 颜色分类

    75. 颜色分类

    给定一个包含红色、白色和蓝色,一共 n 个元素的数组,原地对它们进行排序,使得相同颜色的元素相邻,并按照红色、白色、蓝色顺序排列。

    此题中,我们使用整数 0、 1 和 2 分别表示红色、白色和蓝色。

    注意:
    不能使用代码库中的排序函数来解决这道题。

    示例:

    输入: [2,0,2,1,1,0]
    输出: [0,0,1,1,2,2]
    

    进阶:

    • 一个直观的解决方案是使用计数排序的两趟扫描算法。
      首先,迭代计算出0、1 和 2 元素的个数,然后按照0、1、2的排序,重写当前数组。
    • 你能想出一个仅使用常数空间的一趟扫描算法吗?

    https://leetcode-cn.com/problems/sort-colors/

    暴力

    首先遍历一遍原数组,分别记录 0,1,2 的个数。
    - 然后更新原数组,按个数分别赋上 0,1,2。

    c++

    class Solution {
    public:
        void sortColors(vector<int>& nums) {
            vector<int> colors(3);
            for (int num : nums) ++colors[num];
            for (int i = 0, cur = 0; i < 3; ++i) {
                for (int j = 0; j < colors[i]; ++j) {
                    nums[cur++] = i;
                }
            }
        }
    };
    

    双指针

    题目中还要让只遍历一次数组来求解,那么就需要用双指针来做,分别从原数组的首尾往中心移动。

    - 定义 red 指针指向开头位置,blue 指针指向末尾位置。

    - 从头开始遍历原数组,如果遇到0,则交换该值和 red 指针指向的值,并将 red 指针后移一位。若遇到2,则交换该值和 blue 指针指向的值,并将 blue 指针前移一位。若遇到1,则继续遍历。

    c++

    class Solution {
    public:
        void sortColors(vector<int>& nums) {
            int red = 0, blue = (int)nums.size() - 1;
            for (int i = 0; i <= blue; ++i) {
                if (nums[i] == 0) {
                    swap(nums[i], nums[red++]);
                } else if (nums[i] == 2) {
                    swap(nums[i--], nums[blue--]);
                } 
            }
        }
    };
    

    Dijkstra

    当然我们也可以使用 while 循环的方式来写,那么就需要一个变量 cur 来记录当前遍历到的位置,参见代码如下:

    c++

    class Solution {
    public:
        void sortColors(vector<int>& nums) {
            int left = 0, right = (int)nums.size() - 1, cur = 0;
            while (cur <= right) {
                if (nums[cur] == 0) {
                    swap(nums[cur++], nums[left++]);
                } else if (nums[cur] == 2) {
                    swap(nums[cur], nums[right--]);
                } else {
                    ++cur;
                }
            }
        }
    };
    

    java

    class Solution {
      /*
      荷兰三色旗问题解
      */
      public void sortColors(int[] nums) {
        // 对于所有 idx < i : nums[idx < i] = 0
        // j是当前考虑元素的下标
        int p0 = 0, curr = 0;
        // 对于所有 idx > k : nums[idx > k] = 2
        int p2 = nums.length - 1;
    
        int tmp;
        while (curr <= p2) {
          if (nums[curr] == 0) {
            // 交换第 p0个和第curr个元素
            // i++,j++
            tmp = nums[p0];
            nums[p0++] = nums[curr];
            nums[curr++] = tmp;
          }
          else if (nums[curr] == 2) {
            // 交换第k个和第curr个元素
            // p2--
            tmp = nums[curr];
            nums[curr] = nums[p2];
            nums[p2--] = tmp;
          }
          else curr++;
        }
      }
    }
    

    python

    class Solution:
        def sortColors(self, nums: List[int]) -> None:
            '''
            荷兰三色旗问题解
            '''
            # 对于所有 idx < p0 : nums[idx < p0] = 0
            # curr是当前考虑元素的下标
            p0 = curr = 0
            # 对于所有 idx > p2 : nums[idx > p2] = 2
            p2 = len(nums) - 1
    
            while curr <= p2:
                if nums[curr] == 0:
                    nums[p0], nums[curr] = nums[curr], nums[p0]
                    p0 += 1
                    curr += 1
                elif nums[curr] == 2:
                    nums[curr], nums[p2] = nums[p2], nums[curr]
                    p2 -= 1
                else:
                    curr += 1
    
  • 相关阅读:
    socket的使用一
    logging模块
    configparser模块
    python中read() readline()以及readlines()用法
    hashlib
    JavaScript中forEach的用法相关
    循环调用是事件绑定中遇到的一些问题
    javascript 中 offsetWidth,clientWidth;offsetHeight,clientHeight的区别
    javascript事件:获取事件对象getEvent函数
    html标签之meta标签
  • 原文地址:https://www.cnblogs.com/wwj99/p/12388895.html
Copyright © 2011-2022 走看看