码农知识堂 - 1000bd
  •   Python
  •   PHP
  •   JS/TS
  •   JAVA
  •   C/C++
  •   C#
  •   GO
  •   Kotlin
  •   Swift
  • 【力扣周赛】第 357 场周赛(⭐反悔贪心)


    文章目录

    • 竞赛链接
    • Q1:6925. 故障键盘
      • 解法1——直接模拟
      • 解法2——双端队列
    • Q2:6953. 判断是否能拆分数组(贪心)
    • Q3:2812. 找出最安全路径⭐
      • 解法1——多源BFS+瓶颈路模型?
      • 解法2——多源BFS + 倒序枚举答案 + 并查集(TODO)
    • Q4:2813. 子序列最大优雅度⭐⭐⭐⭐⭐(反悔贪心)
      • 思路——反悔贪心
      • 代码
      • 相似题目列表
        • LCP 30. 魔塔游戏(堆+贪心)
        • 871. 最低加油次数(堆+贪心)
    • 成绩记录

    竞赛链接

    https://leetcode.cn/contest/weekly-contest-357/

    Q1:6925. 故障键盘

    https://leetcode.cn/problems/faulty-keyboard/
    在这里插入图片描述

    提示:
    1 <= s.length <= 100
    s 由小写英文字母组成
    s[0] != 'i'

    解法1——直接模拟

    遇到 ‘i’ 翻转已有的字符串,其它字符直接添加即可。

    class Solution {
        public String finalString(String s) {
            StringBuilder ans = new StringBuilder();
            for (char ch: s.toCharArray()) {
                if (ch != 'i') ans.append(ch);
                else ans.reverse();
            }
            return ans.toString();
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10

    解法2——双端队列

    用一个变量维护当前翻转了几次,来决定新来的字符添加在开头还是结尾。

    class Solution {
        public String finalString(String s) {
            int f = 0;
            Deque<Character> dq = new ArrayDeque<>();
            for (char ch: s.toCharArray()) {
                if (ch == 'i') f++;
                else {
                    if (f % 2 == 0) dq.offerLast(ch);
                    else dq.offerFirst(ch);
                }
            }
            StringBuilder ans = new StringBuilder();
            for (char ch: dq) ans.append(ch);
            if (f % 2 == 1) ans.reverse();
            return ans.toString();
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17

    Q2:6953. 判断是否能拆分数组(贪心)

    https://leetcode.cn/problems/check-if-it-is-possible-to-split-array/

    在这里插入图片描述

    提示:
    1 <= n == nums.length <= 100
    1 <= nums[i] <= 100
    1 <= m <= 200

    在这里插入图片描述

    class Solution {
        public boolean canSplitArray(List<Integer> nums, int m) {
            int n = nums.size();
            if (n == 1 || n == 2) return true;
            for (int i = 0; i < n - 1; ++i) {
                if (nums.get(i) + nums.get(i + 1) >= m) return true;
            }
            return false;
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10

    Q3:2812. 找出最安全路径⭐

    https://leetcode.cn/problems/find-the-safest-path-in-a-grid/

    在这里插入图片描述

    提示:
    1 <= grid.length == n <= 400
    grid[i].length == n
    grid[i][j] 为 0 或 1
    grid 至少存在一个小偷

    解法1——多源BFS+瓶颈路模型?

    第一遍 bfs 求出各个位置的安全系数。
    第二遍 bfs,将各个位置的安全系数更新为从终点开始的路径上的较小值。

    class Solution {
        int[] dx = new int[]{-1, 0, 1, 0}, dy = new int[]{0, -1, 0, 1};
        
        public int maximumSafenessFactor(List<List<Integer>> grid) {
            int n = grid.size();
            if (grid.get(0).get(0) == 1 || grid.get(n - 1).get(n - 1) == 1) return 0;
            
            int[][] g = new int[n][n], safe = new int[n][n];
            Queue<int[]> q = new LinkedList<>();
    
            // 第一遍多源bfs 求出各个位置的安全系数
            for (int i = 0; i < n; ++i) {
                for (int j = 0; j < n; ++j) {
                    if (grid.get(i).get(j) == 1) {
                        g[i][j] = 1;
                        q.offer(new int[]{i, j});
                    }
                }
            }
            while (!q.isEmpty()) {
                int sz = q.size();
                for (int i = 0; i < sz; ++i) {
                    int[] cur = q.poll();
                    int x = cur[0], y = cur[1];
                    for (int k = 0; k < 4; ++k) {
                        int nx = x + dx[k], ny = y + dy[k];
                        if (nx >= 0 && ny >= 0 && nx < n && ny < n && g[nx][ny] == 0) {
                            q.offer(new int[]{nx, ny});
                            g[nx][ny] = g[x][y] + 1;
                        }
                    }
                }
            }
            
            // 第二遍bfs 从终点出发,求出各个路径的最小安全系数
            q.offer(new int[]{n - 1, n - 1});
            safe[n - 1][n - 1] = g[n - 1][n - 1];
            while (!q.isEmpty()) {
                int[] cur = q.poll();
                int x = cur[0], y = cur[1];
                for (int k = 0; k < 4; ++k) {
                    int nx = x + dx[k], ny = y + dy[k];
                    if (nx >= 0 && ny >= 0 && nx < n && ny < n) {
                        int nsafe = Math.min(g[nx][ny], safe[x][y]);
                        if (nsafe > safe[nx][ny]) {
                            safe[nx][ny] = nsafe;
                            q.offer(new int[]{nx, ny});
                        }
                    }
                }
            }
    
            return safe[0][0] - 1;
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55

    解法2——多源BFS + 倒序枚举答案 + 并查集(TODO)

    https://leetcode.cn/problems/find-the-safest-path-in-a-grid/solutions/2375565/jie-jin-on2-de-zuo-fa-duo-yuan-bfsdao-xu-r5um/

    在这里插入代码片
    
    • 1

    Q4:2813. 子序列最大优雅度⭐⭐⭐⭐⭐(反悔贪心)

    https://leetcode.cn/problems/maximum-elegance-of-a-k-length-subsequence/

    在这里插入图片描述

    提示:
    1 <= items.length == n <= 10^5
    items[i].length == 2
    items[i][0] == profiti
    items[i][1] == categoryi
    1 <= profiti <= 10^9
    1 <= categoryi <= n
    1 <= k <= n

    思路——反悔贪心

    https://leetcode.cn/problems/maximum-elegance-of-a-k-length-subsequence/solutions/2375128/fan-hui-tan-xin-pythonjavacgo-by-endless-v2w1/
    在这里插入图片描述

    更多关于反悔贪心可见:【算法】反悔贪心

    代码

    核心的思想是:x + y^2,枚举 y^2的值,并使得 x 在该枚举值下的值最大,就得到了该枚举值下的最大值。比较得到的所有的最大值就是最终结果了。

    class Solution {
        public long findMaximumElegance(int[][] items, int k) {
            // 把利润从大到小排序
            Arrays.sort(items, (a, b) -> b[0] - a[0]);
            long ans = 0, totalProfit = 0;
            Set<Integer> vis = new HashSet<>();
            Deque<Integer> duplicate = new ArrayDeque<>();
            for (int i = 0; i < items.length; ++i) {
                int profit = items[i][0], category = items[i][1];
                if (i < k) {
                    totalProfit += profit;
                    if (!vis.add(category)) {
                        // 如果已经有这个类别了,就把当前的放在栈顶
                        duplicate.push(profit);
                    }
                } else if (!duplicate.isEmpty() && vis.add(category)) {
                    // 如果当前栈不为空,且当前种类没有出现过
                    totalProfit += profit - duplicate.pop();    // 修改利润
                }
    
                ans = Math.max(ans, totalProfit + (long) vis.size() * vis.size());
            }
            return ans;
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25

    相似题目列表

    做完之后感觉这两个题目更相似一些,但是和反悔贪心关系不是那么大。

    LCP 30. 魔塔游戏(堆+贪心)

    https://leetcode.cn/problems/p0NxJO/description/

    在这里插入图片描述
    提示:
    1 <= nums.length <= 10^5
    -10^5 <= nums[i] <= 10^5

    先检查是否有答案存在。

    如果有答案存在,就将已经枚举到的负值放入堆中,每次 s <= 0 时,就取出最小的那个负数移动到末尾即可。

    class Solution {
        public int magicTower(int[] nums) {
            if (Arrays.stream(nums).sum() < 0) return -1;
            int ans = 0;
            // pq中存放目前遇到的负数
            PriorityQueue<Integer> pq = new PriorityQueue<>();
            long s = 1;
            for (int x: nums) {
                s += x;
                if (x < 0) pq.offer(x);
                while (s <= 0) {
                    // 每次把最小的移动到最后面去
                    s -= pq.poll();
                    ans++;
                }
            }
            return ans;
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19

    871. 最低加油次数(堆+贪心)

    https://leetcode.cn/problems/minimum-number-of-refueling-stops/

    在这里插入图片描述

    提示:
    1 <= target, startFuel <= 10^9
    0 <= stations.length <= 500
    1 <= positioni < positioni+1 < target
    1 <= fueli < 10^9

    用堆维护目前可以加的油,但是先不加,等到走不动了再一个个加。

    class Solution {
        public int minRefuelStops(int target, int startFuel, int[][] stations) {
            if (startFuel >= target) return 0;
    
            Arrays.sort(stations, (x, y) -> x[0] - y[0]);   // 按照位置排序
            PriorityQueue<Integer> pq = new PriorityQueue<Integer>((x, y) -> y - x);
            int p = startFuel, ans = 0;
            for (int i = 0; i < stations.length; ++i) {
                while (p < stations[i][0] && !pq.isEmpty()) {
                    p += pq.poll();
                    ans++;
                }
                if (p < stations[i][0]) break;
                if (p >= target) return ans;
                pq.offer(stations[i][1]);
            }
            while (p < target && !pq.isEmpty()) {
                p += pq.poll();
                ans++;
            }
            return p < target? -1: ans;
        }
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23

    成绩记录

    在这里插入图片描述

    T3 借助了一些些外力。

    在这里插入图片描述
    上小分。

  • 相关阅读:
    sql explain
    使用IVX来创造一个自己的3D小游戏【后台和中台、React Core、three.js、Pixi.js、Krpano、antD......】
    小程序开发的部分功能
    C语言-求一个整数储存在内存中的二进制中1的个数
    IO流低级流
    STM32CubeMX学习笔记-CAN接口使用
    Hive分组排序取topN的sql查询示例
    关联规则挖掘(下):数据分析 | 数据挖掘 | 十大算法之一
    从数字化到智能化再到智慧化,智慧公厕让城市基础配套更“聪明”
    gorm的简单操作
  • 原文地址:https://blog.csdn.net/qq_43406895/article/details/132129596
  • 最新文章
  • 攻防演习之三天拿下官网站群
    数据安全治理学习——前期安全规划和安全管理体系建设
    企业安全 | 企业内一次钓鱼演练准备过程
    内网渗透测试 | Kerberos协议及其部分攻击手法
    0day的产生 | 不懂代码的"代码审计"
    安装scrcpy-client模块av模块异常,环境问题解决方案
    leetcode hot100【LeetCode 279. 完全平方数】java实现
    OpenWrt下安装Mosquitto
    AnatoMask论文汇总
    【AI日记】24.11.01 LangChain、openai api和github copilot
  • 热门文章
  • 十款代码表白小特效 一个比一个浪漫 赶紧收藏起来吧!!!
    奉劝各位学弟学妹们,该打造你的技术影响力了!
    五年了,我在 CSDN 的两个一百万。
    Java俄罗斯方块,老程序员花了一个周末,连接中学年代!
    面试官都震惊,你这网络基础可以啊!
    你真的会用百度吗?我不信 — 那些不为人知的搜索引擎语法
    心情不好的时候,用 Python 画棵樱花树送给自己吧
    通宵一晚做出来的一款类似CS的第一人称射击游戏Demo!原来做游戏也不是很难,连憨憨学妹都学会了!
    13 万字 C 语言从入门到精通保姆级教程2021 年版
    10行代码集2000张美女图,Python爬虫120例,再上征途
Copyright © 2022 侵权请联系2656653265@qq.com    京ICP备2022015340号-1
正则表达式工具 cron表达式工具 密码生成工具

京公网安备 11010502049817号