zoukankan      html  css  js  c++  java
  • LeetCode刷题191118

      博主渣渣一枚,刷刷leetcode给自己瞅瞅,大神们由更好方法还望不吝赐教。题目及解法来自于力扣(LeetCode),传送门

    算法:

    给定一个包含 m x n 个元素的矩阵(m 行, n 列),请按照顺时针螺旋顺序,返回矩阵中的所有元素。

    示例 1:

    输入:
    [
    [ 1, 2, 3 ],
    [ 4, 5, 6 ],
    [ 7, 8, 9 ]
    ]
    输出: [1,2,3,6,9,8,7,4,5]
    示例 2:

    输入:
    [
    [1, 2, 3, 4],
    [5, 6, 7, 8],
    [9,10,11,12]
    ]
    输出: [1,2,3,4,8,12,11,10,9,5,6,7]

    解:

    public class Solution {
        public IList<int> SpiralOrder(int[][] matrix)
            {
                if (matrix.Length == 0)
                {
                    return new List<int>();
                }
    
                int minRow = 0;
                int minColumn = 0;
                int maxRow = matrix.GetLength(0) - 1;
                int maxColumn = matrix[0].GetLength(0) - 1;
    
                var seen = new List<List<bool>>();
    
                for (int i = 0; i <= maxRow; i++)
                {
                    var x = new List<bool>();
    
                    for (int j = 0; j <= maxColumn; j++)
                    {
                        x.Add(false);
                    }
    
                    seen.Add(x);
                }
    
                var dr = new int[] { 0, 1, 0, -1 };
                var dc = new int[] { 1, 0, -1, 0 };
    
                int r = 0, c = 0, di = 0;
    
                var result = new List<int>();
    
                for (int i = 0; i < (maxRow + 1) * (maxColumn + 1); i++)
                {
                    result.Add(matrix[r][c]);
                    seen[r][c] = true;
    
                    var nextr = r + dr[di];
                    var nextc = c + dc[di];
    
                    if (nextr >= 0 && nextr <= maxRow && nextc >= 0 && nextc <= maxColumn && !seen[nextr][nextc])
                    {
                        r = nextr;
                        c = nextc;
                    }
                    else
                    {
                        di = (di + 1) % 4;
                        r = r + dr[di];
                        c = c + dc[di];
                    }
                }
    
                return result;
            }
    }

      这道题说来惭愧,渣渣二狗一开始做出来的没有完全通过验证。仔细分析一下,重点在于解决“转向”所引发的问题。换句话说,如果单纯输出一行或一列,无论是正行或逆向都是很容易的。无非就是行索引或者列索引的自增或自减。上面的解法是官方给的一种思路。重点其实在于dr,dc,与di以及seen数组的定义。

      先来说说seen,这个数组是和要处理的数组matrix相同的规模,储存的内容表示对应的matrix节点有没有被访问过。当我们旋转行进的方向旋转了三次之后,放入result中的顺序其实是第一列由下自上的,这样再回到第[0][0]时,我们可以利用seen[0][0]判断出需要进行转向了。

      再来看看dr,dc与di。dr与dc可以理解为一个“向量”,表示当前在matrix中应该前进的方向。如第一组值,dr为0,dc为1,代表每次移动时向column的正向(→)移动。每当我们放入result中一个值之后,利用dr,dc与di来决定下一个要放入result中的值的行与列的索引。当行进至边界值时,我们获取到的新的索引nextr与nextc其实是不存在的,这时可以利用nextr与nextc与对应的边界进行比较来判断。一旦发生这种情况,我们就需要调整行进的方向,因此对di进行处理。

      二狗自己的代码想了想也决定贴出来,失败的原因在于两点:1.边界值没有好好想清楚,把问题复杂化。2.处理数据的逻辑与进行循环的变量交杂在一起,产生歧义与影响。

    public class Solution {
        public IList<int> SpiralOrder(int[][] matrix)
            {
                int minRow = 0;
                int minColumn = 0;
                int maxRow = matrix.GetLength(0) - 1;
                int maxColumn = matrix[0].GetLength(0) - 1;
    
                var seen = new List<List<bool>>();
    
                for (int i = 0; i <= maxRow; i++)
                {
                    var x = new List<bool>();
    
                    for (int j = 0; j <= maxColumn; j++)
                    {
                        x.Add(false);
                    }
    
                    seen.Add(x);
                }
    
                var dr = new int[] { 0, 1, 0, -1 };
                var dc = new int[] { 1, 0, -1, 0 };
    
                int r = 0, c = 0, di = 0;
    
                var result = new List<int>();
    
                for (int i = 0; i < (maxRow + 1) * (maxColumn + 1); i++)
                {
                    result.Add(matrix[r][c]);
                    seen[r][c] = true;
    
                    var nextr = r + dr[di];
                    var nextc = c + dc[di];
    
                    if (nextr >= 0 && nextr <= maxRow && nextc >= 0 && nextc <= maxColumn && !seen[nextr][nextc])
                    {
                        r = nextr;
                        c = nextc;
                    }
                    else
                    {
                        di = (di + 1) % 4;
                        r = r + dr[di];
                        c = c + dc[di];
                    }
                }
    
                return result;
            }
    }

    数据库:

    某网站包含两个表,Customers 表和 Orders 表。编写一个 SQL 查询,找出所有从不订购任何东西的客户。

    Customers 表:

    +----+-------+
    | Id | Name |
    +----+-------+
    | 1 | Joe |
    | 2 | Henry |
    | 3 | Sam |
    | 4 | Max |
    +----+-------+
    Orders 表:

    +----+------------+
    | Id | CustomerId |
    +----+------------+
    | 1 | 3 |
    | 2 | 1 |
    +----+------------+
    例如给定上述表格,你的查询应返回:

    +-----------+
    | Customers |
    +-----------+
    | Henry |
    | Max |
    +-----------+

     

    解:

      很简单,就exists的简单应用。

    select
    c.Name as Customers
    from Customers c
    where not exists
    (
      Select *
      from Orders o
      where o.CustomerId = c.Id
    )

      当然也可以用左连接或者not in的方式完成。

      

  • 相关阅读:
    Qt 学习之路:元素布局
    Qt 学习之路 2(80):定位器
    Qt 学习之路 2(79):QML 组件
    Qt 学习之路:QML 组件
    Qt 学习之路:QML 基本元素
    qt 学习之路 :QML 语法
    Qt 学习之路:QML 和 QtQuick 2
    Qt 学习之路:线程总结
    Qt 学习之路:线程和 QObject
    五步教你实现使用Nginx+uWSGI+Django方法部署Django程序
  • 原文地址:https://www.cnblogs.com/dogtwo0214/p/11883709.html
Copyright © 2011-2022 走看看