【力扣周赛】第 358 场周赛

news2024/10/6 10:31:14

文章目录

  • 竞赛链接
  • Q1:6939. 数组中的最大数对和
  • Q2:6914. 翻倍以链表形式表示的数字
    • 竞赛时代码——存入列表再计算
    • 解法2——只有下一个节点大于 4 的时候,才会因为进位多加一
  • Q3:7022. 限制条件下元素之间的最小绝对差
    • 竞赛时代码——手写二分
    • 写法2——使用API(TreeSet)
  • Q4:7023. 操作使得分最大(大杂烩:数学 + 单调栈(贡献法) + 贪心)
    • 竞赛时代码
    • 相关子题目
      • 质因数分解
        • 求质因数分解
        • 求质因数的数量
      • 快速幂
  • 成绩记录

竞赛链接

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

Q1:6939. 数组中的最大数对和

https://leetcode.cn/problems/max-pair-sum-in-an-array/

在这里插入图片描述
提示:

2 <= nums.length <= 100
1 <= nums[i] <= 10^4

竞赛时代码—— O ( n 2 ) O(n^2) O(n2)

class Solution {
    public int maxSum(int[] nums) {
        int ans = -1, n = nums.length;
        for (int i = 0; i < n; ++i) {
            for (int j = i + 1; j < n; ++j) {
                if (op(nums[i]) == op(nums[j])) {
                    ans = Math.max(ans, nums[i] + nums[j]);
                }
            }
        }
        return ans;
    }
    
    public int op(int n) {
        int res = -1;
        while (n != 0) {
            res = Math.max(res, n % 10);
            n /= 10;
        }
        return res;
    }
}

解法2——一次遍历 O ( n ) O(n) O(n),维护最大数位为 i 的元素的最大值

https://leetcode.cn/problems/max-pair-sum-in-an-array/solutions/2385996/yi-ci-bian-li-by-endlesscheng-6zt9/

在这里插入代码片

Q2:6914. 翻倍以链表形式表示的数字

https://leetcode.cn/problems/double-a-number-represented-as-a-linked-list/

在这里插入图片描述
提示:
链表中节点的数目在范围 [1, 10^4] 内
0 <= Node.val <= 9
生成的输入满足:链表表示一个不含前导零的数字,除了数字 0 本身。

竞赛时代码——存入列表再计算

class Solution {
    public ListNode doubleIt(ListNode head) {
        // 存储列表
        List<Integer> ls = new ArrayList<>();
        while (head != null) {
            ls.add(head.val);
            head = head.next;
        }
        // 计算乘法
        int n = ls.size(), c = 0;
        for (int i = n - 1; i >= 0; --i) {
            int v = ls.get(i) * 2 + c;
            ls.set(i, v % 10);
            c = v / 10;
        }
        // 存入链表
        ListNode dummy = new ListNode(-1), prev = dummy;
        if (c == 1) ls.add(0, 1);
        for (int i = 0; i < n + c; ++i) {
            ListNode cur = new ListNode(ls.get(i));
            prev.next = cur;
            prev = cur;
        }
        return dummy.next;
    }
}

解法2——只有下一个节点大于 4 的时候,才会因为进位多加一

如果不考虑进位,就是每个节点的值乘以 2。
什么时候会受到进位的影响呢?只有下一个节点大于 4 的时候,才会因为进位多加一。
特别地,如果链表头的值大于 4,那么需要在前面插入一个新的节点。

class Solution {
    public ListNode doubleIt(ListNode head) {
        if (head.val > 4) head = new ListNode(0, head);
        for (ListNode cur = head; cur != null; cur = cur.next) {
            cur.val = cur.val * 2 % 10;
            if (cur.next != null && cur.next.val > 4) cur.val++;
        }
        return head;
    }
}

Q3:7022. 限制条件下元素之间的最小绝对差

https://leetcode.cn/problems/minimum-absolute-difference-between-elements-with-constraint/description/

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

竞赛时代码——手写二分

枚举 i 和 j ,其中 j = i + x,这样从 0 ~ i 范围内都是 nums[j] 可以配对的数字。
将 0 ~ i 的数字排序之后,就可以使用二分查找寻找其中最接近 nums[j] 的数字了。

class Solution {
    public int minAbsoluteDifference(List<Integer> nums, int x) {
        int n = nums.size(), ans = Integer.MAX_VALUE;
        List<Integer> ls = new ArrayList();         // 维护前面元素的有序序列(升序)
        for (int i = 0, j = x; j < n; ++i, ++j) {
            // 将nums[i]加入有序序列ls,使用二分查找寻找nums[i]应该插入的位置。
            int l = 0, r = ls.size(), v = nums.get(i);
            while (l < r) {
                int mid = l + r >> 1;
                if (ls.get(mid) <= v) l = mid + 1;
                else r = mid;
            }
            ls.add(l, v);
            
            // 使用二分查找寻找前面序列中最后一个<=nums[j]的元素
            l = 0;
            r = ls.size() - 1;
            v = nums.get(j);
            while (l < r) {
                int mid = l + r + 1 >> 1;
                if (ls.get(mid) > v) r = mid - 1;
                else l = mid;
            }
            // 使用和nums[j]最接近的元素更新答案
            ans = Math.min(ans, Math.abs(v - ls.get(l)));
            if (l + 1 < ls.size()) ans = Math.min(ans, Math.abs(ls.get(l + 1) - v));
        }
        return ans;
    }
}

写法2——使用API(TreeSet)

排序 和 二分查找的过程都可以使用 JDK 来实现。

class Solution {
    public int minAbsoluteDifference(List<Integer> nums, int x) {
        int n = nums.size(), ans = Integer.MAX_VALUE;
        TreeSet<Integer> s = new TreeSet<>();
        s.add(Integer.MAX_VALUE);
        s.add(Integer.MIN_VALUE / 2);
        for (int i = x; i < n; ++i) {
            s.add(nums.get(i - x));
            int y = nums.get(i);
            ans = Math.min(ans, Math.min(s.ceiling(y) - y, y - s.floor(y)));
        }
        return ans;
    }
}

TreeSet 会自动排序,关于 TreeSet 可见:https://docs.oracle.com/en/java/javase/11/docs/api/java.base/java/util/TreeSet.html#ceiling(E)

在这里插入图片描述

floor():返回集合中小于或等于给定元素的最大元素,如果没有这样的元素,则返回null。
ceiling():返回集合中大于或等于给定元素的最小元素,如果不存在这样的元素则返回null。

Q4:7023. 操作使得分最大(大杂烩:数学 + 单调栈(贡献法) + 贪心)

https://leetcode.cn/problems/apply-operations-to-maximize-score/

在这里插入图片描述

提示:
1 <= nums.length == n <= 10^5
1 <= nums[i] <= 10^5
1 <= k <= min(n * (n + 1) / 2, 10^9)

竞赛时代码

我们考虑每个数字 x 对应的 l ~ r 的范围,就是元素 x 可以被选择的次数。
一共可以选择 k 次,所以我们应该将元素按照贡献的能力排序,尽量选贡献大的,其中每个元素 x 可以被选择的次数通过单调栈求出 l ~ r 的范围即可。

质数分数的求法:质因数分解。
k 次操作之后的分数的求法:因为 k 可能很大,所以需要使用快速幂。

class Solution {
    final long MOD = (long)1e9 + 7;
    
    public int maximumScore(List<Integer> nums, int k) {
        int n = nums.size();
        int[][] scores = new int[n][2];
        for (int i = 0; i < n; ++i) {
            scores[i][0] = op(nums.get(i));         // 求质数分数
        }
        Deque<Integer> stk = new ArrayDeque<>();
        int[] l = new int[n], r = new int[n];       // 存储各个元素对应可以选择的l~r范围
        Arrays.fill(l, -1);
        Arrays.fill(r, n);
        
        for (int i = 0; i < n; ++i) {
            while (!stk.isEmpty() && scores[i][0] > scores[stk.peek()][0]) {
                r[stk.pop()] = i;
            }
            if (!stk.isEmpty()) l[i] = stk.peek();
            stk.push(i);
        }
        for (int i = 0; i < n; ++i) {
            scores[i][0] = nums.get(i);             // 元素的贡献
            scores[i][1] = (r[i] - i) * (i - l[i]); // 元素可以被选择的次数
        }
        
        // 排序+贪心找 k次操作对应哪些元素
        Arrays.sort(scores, (x, y) -> y[0] - x[0]);     // 分数倒序排序
        int sum = 0, id = 0, c = 0;
        for (int i = 0; i < n; ++i) {
            if (sum + scores[i][1] <= k) {
                sum += scores[i][1];
                id = i;
                c = scores[i][1];
            }
            else {
                id = i;
                c = k - sum;
                break;
            }
        }
        
        long ans = 1;
        ans = (ans * qmi((long)scores[id][0], (long)c)) % MOD;  // 把最后一个选c次的放进去
        for (int i = id - 1; i >= 0; --i) {
            ans = (ans * qmi((long)scores[i][0], (long)scores[i][1])) % MOD;
        }
        return (int)ans;
    }
    
    // 质因数分解 得到不同质因数的数量
    public int op(int x) {
        int res = 0;
        for (int i = 2; i <= x / i; ++i) {
            if (x % i == 0) {
                res++;
                while (x % i == 0) {
                    x /= i;
                }
            }
        }
        if (x > 1) res++;
        return res;
    }
    
    // 快速幂
    public long qmi(long a, long b) {
        long p = MOD;
        long res = 1 % p, t = a;
        while (b != 0) {
            if ((b & 1) == 1) res = res * t % p;
            t = t * t % p;
            b >>= 1;
        }
        return res;
    }
}

相关子题目

质因数分解

求质因数分解

867. 分解质因数 https://www.acwing.com/problem/content/869/
见:https://blog.csdn.net/qq_43406895/article/details/131843296

import java.util.*;

public class Main {
    public static void main(String[] args){
        Scanner sc = new Scanner(System.in);
        int n = sc.nextInt();
        while (n-- != 0) {
            divide(sc.nextInt());
        }
    }

    static void divide(int x) {
        for (int i = 2; i <= x / i; ++i) {
            if (x % i == 0) {
                int s = 0;
                while (x % i == 0) {        // 把 x 中的 i 除干净
                    s++;
                    x /= i;
                }
                System.out.println(i + " " + s);
            }
        }
        if (x > 1) System.out.println(x + " " + 1);     // 注意要判断最后剩下的没被除掉的质因数
        System.out.println();
    }
}

求质因数的数量

如果是只求质因数的数量的话,那么可以在筛质数的过程中记录质因数的数量。

对应解决这道题目的代码如下:

class Solution {
    final long MOD = (long)1e9 + 7;
    final static int MX = (int)1e5 + 1;
	
	// 求各个数字的不同质因数的数量
    static int[] omega = new int[MX];
    static {
        for (int i = 2; i < MX; ++i) {
            if (omega[i] == 0) {    // i 是质数
                for (int j = i; j < MX; j += i) {
                    omega[j]++;     // i 是 j 的一个质因子
                }
            }
        }
    }
    
    public int maximumScore(List<Integer> nums, int k) {
        int n = nums.size();
        int[][] scores = new int[n][2];
        for (int i = 0; i < n; ++i) {
            scores[i][0] = op(nums.get(i));         // 求质数分数
        }
        Deque<Integer> stk = new ArrayDeque<>();
        int[] l = new int[n], r = new int[n];       // 存储各个元素对应可以选择的l~r范围
        Arrays.fill(l, -1);
        Arrays.fill(r, n);
        
        for (int i = 0; i < n; ++i) {
            while (!stk.isEmpty() && scores[i][0] > scores[stk.peek()][0]) {
                r[stk.pop()] = i;
            }
            if (!stk.isEmpty()) l[i] = stk.peek();
            stk.push(i);
        }
        for (int i = 0; i < n; ++i) {
            scores[i][0] = nums.get(i);             // 元素的贡献
            scores[i][1] = (r[i] - i) * (i - l[i]); // 元素可以被选择的次数
        }
        
        // 排序+贪心找 k次操作对应哪些元素
        Arrays.sort(scores, (x, y) -> y[0] - x[0]);     // 分数倒序排序
        int sum = 0, id = 0, c = 0;
        for (int i = 0; i < n; ++i) {
            if (sum + scores[i][1] <= k) {
                sum += scores[i][1];
                id = i;
                c = scores[i][1];
            }
            else {
                id = i;
                c = k - sum;
                break;
            }
        }
        
        long ans = 1;
        ans = (ans * qmi((long)scores[id][0], (long)c)) % MOD;  // 把最后一个选c次的放进去
        for (int i = id - 1; i >= 0; --i) {
            ans = (ans * qmi((long)scores[i][0], (long)scores[i][1])) % MOD;
        }
        return (int)ans;
    }
    
    // 质因数分解 得到不同质因数的数量
    public int op(int x) {
        return omega[x];
    }
    
    // 快速幂
    public long qmi(long a, long b) {
        long p = MOD;
        long res = 1 % p, t = a;
        while (b != 0) {
            if ((b & 1) == 1) res = res * t % p;
            t = t * t % p;
            b >>= 1;
        }
        return res;
    }
}

快速幂

力扣题目链接:https://leetcode.cn/problems/powx-n/
在这里插入图片描述

参见:【算法基础:数学知识】4.4 快速幂

递归版——

    static long qmi(long a, long b, long p) {
        if (b == 0) return 1;
        long res = qmi(a, b / 2, p) % p;
        if (b % 2 == 0) return res * res % p;
        else return res * res * a % p;
    }

迭代版——

    static long qmi(long a, long b, long p) {
        long res = 1 % p, t = a;
        // 把 b 看成二进制数字,哪些位置是 1 就把它乘起来就好了
        while (b != 0) {
            if ((b & 1) == 1) res = res * t % p;
            t = t * t % p;
            b >>= 1;
        }
        return res;
    }

成绩记录

在这里插入图片描述

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/878841.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

批量提取文件名到excel,详细的提取步骤

如何批量提取文件名到excel&#xff1f;我们的电脑中可能存储着数量非常多的电子文件&#xff0c;现在需要快速将这些文件的名称全部提取到Excel中。虽然少量数据可以通过复制粘贴的方式轻松完成&#xff0c;但是对于上万个数据而言&#xff0c;复制粘贴都是行不通的&#xff0…

【考研数学】高等数学第三模块——积分学 | Part II 定积分(反常积分及定积分应用)

文章目录 前言三、广义积分3.1 敛散性概念&#xff08;一&#xff09;积分区间为无限的广义积分&#xff08;二&#xff09;积分区间有限但存在无穷间断点 3.2 敛散性判别法 四、定积分应用写在最后 前言 承接前文&#xff0c;梳理完定积分的定义及性质后&#xff0c;我们进入…

陪诊小程序开发|陪诊陪护小程序让看病不再难

陪诊小程序通过与医疗机构的合作&#xff0c;整合了医疗资源&#xff0c;让用户能够更加方便地获得专业医疗服务。用户不再需要面对繁琐的挂号排队&#xff0c;只需通过小程序预约服务&#xff0c;便能够享受到合适的医疗资源。这使得用户的就医过程变得简单高效&#xff0c;并…

vue基础知识三:v-show和v-if有什么区别?使用场景分别是什么?

一、v-show与v-if的共同点 我们都知道在 vue 中 v-show 与 v-if 的作用效果是相同的(不含v-else)&#xff0c;都能控制元素在页面是否显示 在用法上也是相同的 <Model v-show"isShow" /> <Model v-if"isShow" />当表达式为true的时候&#…

使用 Python 在 NLP 中进行文本预处理

一、说明 自然语言处理 &#xff08;NLP&#xff09; 是人工智能 &#xff08;AI&#xff09; 和计算语言学的一个子领域&#xff0c;专注于使计算机能够理解、解释和生成人类语言。它涉及计算机和自然语言之间的交互&#xff0c;允许机器以对人类有意义和有用的方式处理、分析…

Debian 10驱动Broadcom 无线网卡

用lspci命令查询无线网卡品牌&#xff1a; 运行下面代码后&#xff0c;重启即可。 apt-get install linux-image-$(uname -r|sed s,[^-]*-[^-]*-,,) linux-headers-$(uname -r|sed s,[^-]*-[^-]*-,,) broadcom-sta-dkms

Springboot MultipartFile文件上传与下载

yml文件配置是否可以上传及上传附件大小 servlet:multipart:# 允许文件上传enabled: true# 单个文件大小max-file-size: 20MB# 设置总上传的文件大小max-request-size: 50MB /*** param files* param request* Description 上传文件* Throws* Return java.util.List* Date 202…

Dynamics 365 视图

1 视图分类 如图,视图分为查找视图、关联视图、公共视图三类。其中查找视图又可分为查找视图、高级查找视图、快速查找视图。 查找视图从名称来看,就是查找记录使用的,相当于预置了一些过滤条件,且控制查询的结果展示的列。只不过使用的位置不同,具体如下。 公共视图是最…

实践-CNN卷积层

实践-CNN卷积层 1 卷积层构造2 整体流程3 BatchNormalization效果4 参数对比5 测试效果 1 卷积层构造 2 整体流程 根据网络结构来写就可以了。 池化 拉平 训练一个网络需要2-3天的时间。用经典网络来&#xff0c;一些细节没有必要去扣。 损失函数&#xff1a; fit模型&…

量子计算的突破:从理论到实践

章节一&#xff1a;引言 随着信息时代的到来&#xff0c;计算科学与技术也在不断迎来新的突破与革新。其中&#xff0c;量子计算作为一项引人瞩目的前沿技术&#xff0c;正逐渐从理论走向实践。量子计算以其在处理复杂问题上的巨大潜力&#xff0c;吸引着全球科学家和工程师的关…

需求调研前需要做哪些准备?

大家好&#xff0c;我是沐尘而生&#xff0c;今天让我和大家一起走进&#xff0c;产品经理实战百问百答&#xff0c;从问题入手&#xff0c;一步一个脚印&#xff0c;习惯产品经理岗位。 我将从需求调研的角度出发&#xff0c;为大家详细介绍一下在开始调研前需要做哪些准备工作…

项目难点:解决IOS调用起软键盘之后页面样式布局错乱问题

需求背景 &#xff1a; 开发了一个问卷系统重构项目&#xff0c;刚开始开发的为 PC 端&#xff0c;其中最头疼的一点无非就是 IE 浏览器的兼容适配性问题&#xff1b; 再之后项目经理要求开发移动端&#xff0c;简单的说就是写 H5 页面&#xff0c;到时候会内嵌在 App 应用或办…

嵌入式要卷成下一个Java了吗?

不会&#xff01; 说不会也是有自己的原因的 前几天写了一篇 Linux 和单片机的文章 不做Linux就没前途吗&#xff1f; 单片机容易&#xff0c;门槛低&#xff0c;无非不就是单片机技术知识点比较少&#xff0c;特别是面向过程式的编程也更容易掌握。嵌入式 Linux 是多任务式的&…

Rx.NET in Action 第四章学习笔记

Part 2 核心思想 《Rx.NET in Action》这一部共分八章&#xff0c;涵盖了Rx 关键模块——**Observable(可观察序列)和Observer(观察者)**的全部功能&#xff0c;以及如何创建它们、连接它们和控制它们之间的关系。 然后&#xff0c;您将学习如何使用强大的 Rx 处理器构建复杂…

小程序云开发配置访问公网链接--定位到具体街道地址

以获取定位地址为例&#xff1a; 一、和平常用postman、talend api tester、其他测试调用工具为比对&#xff1b; 现有一需求&#xff0c;需要定位当前地址&#xff0c; 具体详细文档&#xff1a;腾讯位置服务 参数准备工作&#xff1a; key&#xff1a;是在腾讯位置服务里面注…

使用路由器更改设备IP_跨网段连接PLC

在一些设备IP已经固定,但是需要采集此设备的数据,需要用到跨网段采集 1、将路由器WAN&#xff08;外网拨号口&#xff09;设置为静态IP 2、设置DMZ主机&#xff0c;把DMZ主机地址设置成跨网段的PLC地址 DMZ主机 基本信息. DMZ (Demilitarized Zone)即俗称的非军事区&#xff0…

【Unity造轮子】制作一个简单的2d抓勾效果(类似蜘蛛侠的技能)

前言 欢迎阅读本文&#xff0c;本文将向您介绍如何使用Unity游戏引擎来实现一个简单而有趣的2D抓勾效果&#xff0c;类似于蜘蛛侠的独特能力。抓勾效果是许多动作游戏和平台游戏中的常见元素&#xff0c;给玩家带来了无限的想象和挑战。 不需要担心&#xff0c;即使您是一…

服务器扩展未生效

服务器扩容未生效 在阿里云付费扩容后&#xff0c;在服务器里面看未生效。 阿里云->实例与镜像->实例->选择实例->云盘->扩容进入linux服务器查看&#xff1a; df -h vda1扩容未生效。原40g->扩容后100g 解决方法&#xff1a; 1、安装growpart yum inst…

chatgpt和xmind结合起来帮你制作精美的思维导图

介绍 chatgpt和xmind结合起来帮你制作精美的思维导图。 1.输出Markdown格式 2.xmind导入.md文件

自动驾驶技术:改变交通出行的未来

自动驾驶技术&#xff0c;这个让人充满期待的技术&#xff0c;正在改变我们的交通方式&#xff0c;带来一种全新的出行体验。它可以让汽车、无人机等交通工具像人类驾驶一样自主行驶&#xff0c;通过人工智能、视觉计算、雷达、监控装置和全球定位系统协同合作&#xff0c;实现…