【力扣周赛】第 357 场周赛(⭐反悔贪心)

这篇具有很好参考价值的文章主要介绍了【力扣周赛】第 357 场周赛(⭐反悔贪心)。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

竞赛链接

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

Q1:6925. 故障键盘

https://leetcode.cn/problems/faulty-keyboard/
【力扣周赛】第 357 场周赛(⭐反悔贪心),算法刷题记录,leetcode,算法,反悔贪心,贪心,堆

提示:
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();
    }
}

解法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();
    }
}

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

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

【力扣周赛】第 357 场周赛(⭐反悔贪心),算法刷题记录,leetcode,算法,反悔贪心,贪心,堆

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

【力扣周赛】第 357 场周赛(⭐反悔贪心),算法刷题记录,leetcode,算法,反悔贪心,贪心,堆

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;
    }
}

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

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

【力扣周赛】第 357 场周赛(⭐反悔贪心),算法刷题记录,leetcode,算法,反悔贪心,贪心,堆

提示:
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;
    }
}

解法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/

在这里插入代码片

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

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

【力扣周赛】第 357 场周赛(⭐反悔贪心),算法刷题记录,leetcode,算法,反悔贪心,贪心,堆

提示:
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/
【力扣周赛】第 357 场周赛(⭐反悔贪心),算法刷题记录,leetcode,算法,反悔贪心,贪心,堆

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

代码

核心的思想是: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;
    }
}

相似题目列表

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

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

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

【力扣周赛】第 357 场周赛(⭐反悔贪心),算法刷题记录,leetcode,算法,反悔贪心,贪心,堆
提示:
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;
    }
}

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

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

【力扣周赛】第 357 场周赛(⭐反悔贪心),算法刷题记录,leetcode,算法,反悔贪心,贪心,堆

提示:
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;
    }
}

成绩记录

【力扣周赛】第 357 场周赛(⭐反悔贪心),算法刷题记录,leetcode,算法,反悔贪心,贪心,堆

T3 借助了一些些外力。

【力扣周赛】第 357 场周赛(⭐反悔贪心),算法刷题记录,leetcode,算法,反悔贪心,贪心,堆
上小分。文章来源地址https://www.toymoban.com/news/detail-698387.html

到了这里,关于【力扣周赛】第 357 场周赛(⭐反悔贪心)的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 【力扣周赛】第 113 场双周赛(贪心&异或性质&换根DP)

    https://leetcode.cn/contest/biweekly-contest-113/ https://leetcode.cn/problems/minimum-right-shifts-to-sort-the-array/ 提示: 1 = nums.length = 100 1 = nums[i] = 100 nums 中的整数互不相同。 因为数据范围很小,所以可以从小到大枚举可能的答案。 https://leetcode.cn/problems/minimum-array-length-after-pair-removals/ 提示: 1

    2024年02月07日
    浏览(32)
  • leetcode第 357/358 场周赛

    可能别人有更好的解法,我这写法是不断往线段树中插入数值,每次先插入nums[i-x],然后搜索(1到i)中的最大值和(i到max)中的最小值去更新ans。 看了看别人题解,直接用set写是真的牛。自己还是见识短浅了。 暴力乱搞,考虑两种极端情况,一种无脑选profit大的,一种优先选

    2024年02月12日
    浏览(39)
  • 【算法】力扣第 284 场周赛(最短代码)

    看数据范围 1 = nums.length = 1000 ,直接暴力 2行 搞定 看数据范围 1 = n = 1000 ,每个工件最多只覆盖4个单元格,直接哈希+暴力, 2行搞定 这题比较吃细节,推荐大家看一下灵茶山艾府大佬的题解, 1行 就搞定了 三次dijkstra,可可也是看了题解之后才做出来, 15行 解法👇 T4罚坐一

    2024年02月13日
    浏览(46)
  • 力扣周赛日记350

    早上兴高采烈起床写周赛,结果写完两题开始坐牢。菜的很。 LeetCode 第 350 场周赛 LeetCode 6901. 总行驶距离 2.1.1 题意 卡车两个油箱,耗油1L行驶10km。油箱A耗5L,油箱B给邮箱A油1L。油箱A空后停止行驶,求可行使距离。 2.1.2 分析 开始想O(1)解法,发现这题主要问题在油箱B给了油箱

    2024年02月10日
    浏览(38)
  • 【算法】反悔贪心

    思路是无论当前的选项是否最优都接受,然后进行比较,如果选择之后不是最优了,则反悔,舍弃掉这个选项;否则,正式接受。如此往复。 https://leetcode.cn/problems/course-schedule-iii/description/?envType=daily-questionenvId=2023-09-11 提示: 1 = courses.length = 104 1 = durationi, lastDayi = 104 解法看注

    2024年02月09日
    浏览(25)
  • C++ 算法竞赛、01 周赛篇 | AcWing 第1场周赛

    竞赛 - AcWing 3577. 选择数字 - AcWing题库 暴力两层循环 两个数组的最大值相加一定是新数 3578. 最大中位数 - AcWing题库 整数二分问题。求中位数,并依次递增,计算所需的操作次数。求最后一个操作次数总和 = k 的中位数值 如果 mid - a[i] 0 ,意味着该数比中位数大, 不需要操作

    2024年02月10日
    浏览(46)
  • C++ 算法竞赛、02 周赛篇 | AcWing 第2场周赛

    竞赛 - AcWing AcWing 3626. 三元一次方程 - AcWing 两层循环 3627. 最大差值 - AcWing题库 考查贪心,所有输入的不是0的数排序,每次操作取最大的数++,由于每个数最大可以是1e9,int可能溢出,需要用 long long 3628. 边的删减 - AcWing题库 刚开始有点傻,打算用克鲁斯卡尔生成最小生成树

    2024年02月10日
    浏览(37)
  • C++ 算法竞赛、03 周赛篇 | AcWing 第4场周赛

    竞赛 - AcWing 3694. A还是B - AcWing题库 简单题 3695. 扩充序列 - AcWing题库 考查递归。可以发现最终序列除中点,左右两段都是相等的,可以依据这个特性来递归 超级长的序列缩小 (log_2n) 次,每次将 k 坐标映射到缩小的各个序列上,k肯定是其中一个序列的中点 3696. 构造有向无环

    2024年02月09日
    浏览(38)
  • C++ 算法竞赛、05 周赛篇 | AcWing 第85场周赛

    竞赛 - AcWing 4791. 死或生 - AcWing题库 简单题 4792. 最大价值 - AcWing题库 贪心,先找到最大价值的字母,往最后面插最大的 4793. 危险程度 - AcWing题库 把图分成若干个连通块,每个连通块假设有 k 个点,最多会反应 k - 1 次 因此题目转变为求连通块数量,假设为 t,答案就是 (2^

    2024年02月09日
    浏览(42)
  • C++ 算法竞赛、07 周赛篇 | AcWing 第120场周赛

    竞赛 - AcWing 5146. 最大GCD - AcWing题库 不难发现,最大公约数的条件是 (GCD(lfloor frac{n}{2} rfloor ,lfloor frac{n}{2} rfloor * 2)) 5147. 数量 - AcWing题库 不含 4 和 7 以外 (Rightarrow) 只含 4 和 7,每位只有两种情况,最多到 1e9,即 (2^9) 个情况,爆搜枚举即可 AcWing 5148. 字符串匹配 -

    2024年02月08日
    浏览(41)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包