程序员基德 level
获赞
203
粉丝
238
关注
3
看过 TA
1195
中国科学技术大学
2026
C++
IP属地:浙江
热爱算法的程序员
私信
关注
------------------------------------题目一:题目大意:给定一个长度为 n (1 <= n <= 1e5) 的序列 a (1 <= a[i] <= n)。你可以执行最多一次操作:选择一个连续区间 [L, R],将区间内所有数字加1。你的目标是最大化操作后能减少的逆序对(能量冲突)数量。(T 组数据)解法思路:核心是分析区间加一操作对逆序对的影响。一个逆序对 (i, j) 会被消除,当且仅当 i 不在区间内,j 在区间内,且 a[i] = a[j] + 1。反之,如果 i 在区间内,j 不在区间内,且 a[i] = a[j],则会产生新的逆序对。为了避免产生新的逆序对,最优策略是选择一个后缀区间 [L, n] 进行操作。问题转化为,对于每个 L,计算选择后缀 [L, n] 能消除多少逆序对。这可以通过从后向前遍历 L,同时用两个计数数组分别维护 L 前后各个数值的出现次数,在 O(n) 时间内计算出每个 L 对应的收益,从而找到最大值。------------------------------------题目二:题目大意:有 n (3 <= m <= n <= 1e5) 位评委,给出 n 个评分。你需要在这 n 个评分中,找到一个长度为 m 的连续区间,使得去掉该区间中的一个最高分和一个最低分后,剩下 m-2 个分数的平均值最大。输出这个最优区间的起始位置(1-indexed)。如果平均值相同,选择起始位置最小的。解法思路:由于分母 m-2 是固定的,最大化平均值等价于最大化分子,即 `区间和 - 区间最大值 - 区间最小值`。这个问题可以用滑动窗口来解决。维护一个长度为 m 的窗口,从左到右滑过整个评分数组。为了能在窗口滑动时(增加一个元素,删除一个元素)高效地找到最大值和最小值,需要一个支持快速增删和查询极值的数据结构。C++ 中的 `multiset` 或 Java 中的 `TreeMap` 非常适合此场景,它们可以在 O(log m) 的时间内完成操作。因此,总的时间复杂度为 O(n log m)。在滑动过程中,不断更新最大得分和对应的起始位置即可。z具体的详细代码和题解可以戳我主页的文章查看
投递京东等公司10个岗位
0 点赞 评论 收藏
分享
------------------------------------题目一:题目大意:有 n (1 <= n <= 1e5) 本书,分为精装本和普通本。你必须执行恰好 k (1 <= k <= 1e9) 次“装帧转换”操作(精装变平装,或平装变精装)。问操作结束后,最多能有多少本精装本。解法思路:这是一个贪心问题。为了最大化精装本数量,应该优先将平装本转换为精装本。统计初始的平装本数量 low_cnt。若 k <= low_cnt,说明操作次数不足以把所有平装本都转换,此时最优策略是花费 k 次操作将 k 本平装本变为精装本,最终精装本数量为 初始数量 + k。若 k > low_cnt,说明可以先把所有平装本都转换成精装本,此时书架上全是精装本,还剩下 k - low_cnt 次操作。对于剩下的操作,每两次操作(精装->平装->精装)可以抵消,不影响最终结果。因此,如果剩余操作是偶数次,最终可以保持全精装;如果是奇数次,则必须消耗一次操作,使得一本精装书变为平装,最终有 n-1 本精装。------------------------------------题目二:题目大意:给定一个 n (2 <= n <= 2e5) 个音符的非严格递增序列 a,和一个音高增量 m (1 <= m <= 1e9)。你可以执行一次操作:选择一个区间 [l, r],对区间内每个音符 ai,其音高变为 ai + (r - i + 1) * m。目标是使得操作后的序列中存在 aj > a(j+1),即打破单调性。求所需的最短区间长度。如果无法做到,输出-1。(T 组数据)解法思路:关键在于分析操作对相邻音符差值的影响。要使 aj > a(j+1),必须让 aj 相对 a(j+1) 增加的音高大于它们原来的差值。分析操作公式可知,在区间内,ai 相对 a(i+1) 会多增加 m;在区间末尾,ar 相对 a(r+1) 也会增加 m。因此,只要存在一个位置 i,使得原始音高差 a(i+1) - ai < m,我们就可以通过操作打破这里的单调性。并且,此时只需选择长度为1的区间 [i, i] 进行操作,只提升 ai 的音高,就足以保证新的 a'i > a(i+1)。因此,只需遍历一遍数组,检查是否存在相邻音符的差值小于 m。如果存在,最短区间长度就是1;如果不存在,则无论如何操作都无法打破单调性,答案是-1。------------------------------------题目三:题目大意:有一个 n x m (1 <= n, m <= 1e9) 的LED灯阵列,初始全为0。经过 k (1 <= k <= 2e5) 次操作,每次操作会翻转指定行或列的状态(0变1,1变0)。所有操作结束后,将整个阵列按行拼接成一个巨大的二进制数,求其对应的十进制值对 1e9 + 7 取模的结果。解法思路:由于翻转操作是异或操作,一个位置 (i, j) 的最终状态只取决于第 i 行和第 j 列被翻转次数的奇偶性。最终状态 `a[i][j] = (row_flip[i] % 2) ^ (col_flip[j] % 2)`。首先遍历 k 次操作,用两个集合记录被翻转了奇数次的行号和列号。设被翻奇数次的行集合为 R,列集合为 C。第 i 行的数值,如果 i 不在 R 中,则其值为 `Sum_{j in C} 2^(m-j)`;如果 i 在 R 中,则其值为 `(2^m - 1) - Sum_{j in C} 2^(m-j)`。最终结果是 `Sum_{i=1 to n} (value_of_row_i * (2^m)^(n-i))`。这个复杂的求和式可以通过提取公因式和等比数列求和公式进行化简,所有的大数幂运算都通过快速幂取模来高效计算。具体的详细代码和题解可以戳我主页的文章查看
投递科大讯飞等公司10个岗位
0 点赞 评论 收藏
分享
------------------------------------题目一:题目大意:有 n (1 <= n <= 2e5) 本书,编号为 ai (0 <= ai <= 1e9)。你需要将它们放入若干个临时书架(先进先出队列),要求奇数编号和偶数编号的书不能混放。最终,你需要从这些书架中按顺序取出书本,形成一个严格递减的序列。问最少需要多少个临时书架。解法思路:奇偶性限制使得奇数和偶数两组书的处理是完全独立的。对于每一组(例如奇数),为了能按顺序取出形成一个严格递减序列,放入同一个书架的书必须是原序列中的一个严格递减子序列。因此,问题转化为:将奇数子序列和偶数子序列分别拆分成最少数目的严格递减子序列。根据Dilworth定理,一个序列最少能被划分成的递减子序列的数量,等于其最长严格递增子序列(LIS)的长度。所以,分别求出奇数序列和偶数序列的LIS长度,两者相加即为答案。LIS可用经典的O(n log n)算法求解。------------------------------------题目二:题目大意:有 n (1 <= n, m <= 1000) 个部门和 m 个项目,部门权重为 ai,项目难度为 bj (1 <= a, b <= 1e4)。还有一个 n x m 的绩效矩阵 vij (1 <= v <= 1e4)。总绩效为所有 wij = vij * (ai + bj) 的和。你可以任意交换部门的顺序(行和a的顺序),也可以任意交换项目的顺序(列和b的顺序),目标是最大化总绩效。解法思路:关键在于对总绩效公式进行数学变形。总绩效 = Sum(vij * (ai + bj)) = Sum(vij*ai) + Sum(vij*bj)。将求和顺序改变可得:Sum(ai * Sum_j(vij)) + Sum(bj * Sum_i(vij))。这等价于 `部门权重向量a` 与 `矩阵行和向量` 的点积,加上 `项目难度向量b` 与 `矩阵列和向量` 的点积。根据排序不等式,两个向量的点积在它们同序排序时最大。因此,先计算出矩阵的所有行和与列和。然后,将部门权重a和行和向量都按降序排序后计算点积,再将项目难度b和列和向量都按降序排序后计算点积,两者相加即为最大总绩效。------------------------------------题目三:题目大意:有 n (1 <= n <= 1e5) 个服务区域,每个区域是数轴上的一个闭区间 [li, ri] (|li|,|ri| <= 1e9)。你需要选择一个整数点 x 作为仓储中心,使得总运输成本最小。单个成本定义为:如果 x 在区间内,成本为0;否则成本是 x 到该区间最近端点的距离。解法思路:这是一个经典的几何中位数问题。总成本函数是所有单个成本函数的和,而每个单个成本函数 `cost(x)` 都是一个V形的凸函数。多个凸函数之和仍然是凸函数,其最小值点可以通过分析斜率变化找到。总成本函数的斜率在每个区间的端点 `li` 和 `ri` 处发生变化。当 x 从负无穷向正无穷移动时,初始总斜率为-n,每经过一个端点,斜率就加1。当斜率从负数变为非负数时,就到达了成本最小的位置。这个位置恰好是所有 `2n` 个端点(所有 `li` 和 `ri` 的集合)的中位数。因此,只需收集所有 `2n` 个端点,找到它们的中位数作为最优选址x,然后计算总成本即可。具体的详细代码和题解可以戳我主页的文章查看
投递阿里巴巴集团等公司10个岗位
0 点赞 评论 收藏
分享
------------------------------------题目一:题目大意:有 n (1 <= n <= 2e5) 颗宝石,每颗有能量值 ai (-n <= ai <= n)。你可以执行任意次“融合”操作:选择两颗宝石 i 和 j,将 j 的能量转移给 i (ai = ai + aj, aj = 0)。目标是最大化所有位置的前缀最大能量值之和,即 sum(max(a1, ..., ai)) for i=1 to n。(T 组数据, 1 <= T <= 1e4)解法思路:关键在于理解融合操作的本质是能量的自由分配。为了最大化前缀最大值之和,最优策略是创造一个尽可能大的数,并放在首位。如果数组中存在正数,就把所有正能量的宝石融合到第一颗上,使其能量变为所有正数之和,其余位置变为0或负数。这样每个前缀的最大值都是这个正数之和。如果所有宝石能量都是非正数,若 n>1,则可以通过融合操作造出一个0,使前缀最大值变为0;若 n=1,则无法操作,答案就是其本身的负能量值。------------------------------------题目二:题目大意:在一片 n x n (2 <= n, m <= 1e6) 的森林中,有 m 名探险者和 n 个救援站。救援站位于对角线 (i, i) 上,每个站只能救一人。探险者会去距离自己最近(曼哈顿距离)的救援站。如果有多个最近的,他们会协调分配以最大化获救人数。求最多能获救的人数。解法思路:此题可转化为区间选点问题。对于一个在 (x, y) 的探险者,其到对角线上救援站 (k, k) 的曼哈顿距离为 |x-k| + |y-k|。可以发现,当 k 落在 [min(x,y), max(x,y)] 区间内时,距离是最小且恒定的。因此,每个探险者对应一个可选的救援站区间。问题就变成了:有 m 个区间,n 个点,每个点最多被一个区间选择,求最多能满足多少个区间。这是一个经典的贪心问题:将所有区间按右端点升序排序,然后遍历区间,为每个区间贪心地分配其范围内最靠左的可用救援站。使用并查集可以高效地找到下一个可用的位置。------------------------------------题目三:题目大意:有 n (1 <= n, q <= 1e5) 个魔法水晶,能量为 ai (1 <= ai <= 1e5)。需要处理 q 次操作,操作分两种:1. 将第 i 个水晶的能量修改为 x;2. 查询区间 [l, r] 内所有水晶能量的波动度(方差)。方差定义为 (1/m) * sum((bi - mean)^2)。解法思路:直接计算方差涉及均值,不便于用数据结构维护。关键是对方差公式进行数学变换:Var(X) = E(X^2) - (E[X])^2。对于一个区间,这等价于`(区间平方和 / 区间长度) - (区间和 / 区间长度)^2`。这样,我们只需要维护区间的和与区间的平方和。这可以用两个树状数组(或线段树)来高效实现:一个树状数组维护 `sum(ai)`,另一个维护 `sum(ai^2)`。单点修改时,在这两个树状数组上都进行更新。区间查询时,分别查出区间和与区间平方和,再代入公式计算即可。具体的详细代码和题解可以戳我主页的文章查看
投递阿里巴巴集团等公司10个岗位
0 点赞 评论 收藏
分享
------------------------------------题目一:题目大意:给定 n (1 <= n <= 2e5) 张数字卡片,每张上有一个正整数 ai (1 <= ai <= 1e9, 不含0)。你需要将所有卡片上的数字拆分成独立的数位,然后将这些数位重新分配,组成 n 个新的数字,但每个新数字的位数必须与原来该位置的卡片上的数字位数相同。目标是让这 n 个新数字的总和最大。解法思路:这是一个贪心问题。要使总和最大,必须让越大的数位处在权重越高的位置上(例如,百位的权重大于十位)。因此,最优解法是:第一步,将所有数字拆分成单个的数位,放入一个列表。第二步,根据所有原始数字的位数,计算出所有位置的权重(如1, 10, 100等),放入另一个列表。第三步,将数位列表和权重列表都按降序排序。最后,将排序后的两个列表中的元素一一对应相乘再求和,即可得到最大的魔法能量值。------------------------------------题目二:题目大意:有一条含 n (1 <= n <= 1000) 颗珠宝的项链,每颗价值为 ai (1 <= ai <= 2e5)。对于每个数量 m (从1到n),你需要从项链的某个前缀中(比如前 i 颗)选出 m 颗珠宝(保持原始相对顺序),并计算成本。成本 = (i - m) * k + (所选m颗珠宝的总价值)。你需要对每个 m,找出其最小的设计成本。(T 组数据, 1 <= T <= 50)解法思路:这是一个动态规划问题。可以定义 `dp[i][j]` 为“选择 i 颗珠宝,且最后一颗是原项链中的第 j 颗时,所选珠宝的最小价值总和”。状态转移方程为:`dp[i][j] = a[j] + min(dp[i-1][p])` 其中 `p < j`。这个转移可以通过维护前缀最小值来优化。得到DP表后,对于每个 m,最终成本是 `min(dp[m][i] + k * (i - m))` for `i >= m`。由于 `dp[i]` 只依赖于 `dp[i-1]`,可以使用滚动数组将空间复杂度优化到 O(n)。------------------------------------题目三:题目大意:给定一个长度为 n (1 <= n <= 2e5) 的非严格递增序列,其中部分数字缺失,用 0 表示 (0 <= ai <= 1e9)。已知序列的第一个和最后一个数不为0。你需要计算有多少种方法填补这些0,使得整个序列仍然保持非严格递增,结果对 1e9 + 7 取模。解法思路:这是组合数学问题。序列中已有的非零数字将整个序列分割成若干个独立的待填补区间。对于任意一个由非零数 L 和 R 包围的区间,假设中间有 c 个0,我们需要在这 c 个位置填上数,使得 L <= a_i <= ... <= a_j <= R。这等价于从 [L, R] 这个范围内的 `R - L + 1` 个数中,可重复地选出 c 个数,方案数符合多重组合(隔板法)模型。公式为 C((R-L)+c, c)。由于 R-L 的值可能很大,需要用 `(N*(N-1)*...*(N-c+1)) / c!` 的形式计算组合数,并使用费马小定理求乘法逆元来处理除法。最终答案是所有独立区间方案数的乘积。具体的详细代码和题解可以戳我主页的文章查看
投递小红书等公司10个岗位
0 点赞 评论 收藏
分享

创作者周榜

更多
关注他的用户也关注了:
牛客网
牛客网在线编程
牛客网题解
牛客企业服务