打卡信奥刷题(3245)用C++实现信奥题 P8563 Magenta Potion
P8563 Magenta Potion
题目描述
给定一个长为 nnn 的整数序列 aaa,其中所有数的绝对值均大于等于 222。有 qqq 次操作,格式如下:
1 i k\texttt{1 i k}1 i k,表示将 aia_iai 修改为 kkk。保证 $k $ 的绝对值大于等于 222。
2 l r\texttt{2 l r}2 l r,考虑 [l,r][l,r][l,r] 的子区间(包括本身)中乘积最大的的区间乘积 MMM。如果 M>230M>2^{30}M>230,输出 Too large,否则输出 MMM。特别地,空区间的元素乘积定义为 111。
输入格式
第一行两个正整数表示 n,qn,qn,q。
第二行输入 nnn 个整数表示 aia_iai。
接下来 qqq 行,每行三个整数表示一次询问,格式见上。
输出格式
对于每次 2\tt22 操作输出一行表示询问的答案。
输入输出样例 #1
输入 #1
5 7
2 2 3 4 5
2 1 5
1 3 -3
2 1 5
2 3 3
1 1 100000
1 2 100000
2 1 2
输出 #1
240
20
1
Too large
说明/提示
对于所有的数据,2≤∣ai∣,∣k∣≤1092\le |a_i|,|k| \le 10^92≤∣ai∣,∣k∣≤109,1≤n,q≤2×1051 \le n,q \le 2\times 10^51≤n,q≤2×105,1≤l≤r≤n1 \le l \le r \le n1≤l≤r≤n。
测试点编号 n,q≤ 特殊限制 1∼2103∼61007∼105×10311∼13A14∼16B17∼20 \def\arraystretch{1.5} \begin{array}{c|c|c}\hline \textbf{测试点编号}&\bm{~~~~~~~~n,q\le~~~~~~~~}&~~~~\textbf{特殊限制}~~~~\cr\hline \textsf1\sim \sf2 & 10& \cr\hline \sf3\sim 6 & 100& \cr\hline \sf7\sim 10 & 5 \times 10^3&\cr\hline \sf 11\sim 13 & &\sf A\cr\hline \sf14\sim 16 & & \sf B\cr\hline \sf17\sim 20 & &\cr\hline \end{array} 测试点编号1∼23∼67∼1011∼1314∼1617∼20 n,q≤ 101005×103 特殊限制 AB
A\textsf AA:保证 ai,k≥2a_i,k \ge 2ai,k≥2。
B\textsf BB:保证对于每一组询问,对应的 r−l≥100r-l \ge 100r−l≥100。
C++实现
#include <bits/stdc++.h>
#define ll long long
#define inf 1<<30
using namespace std;
int n, q;
ll arr[200005];
int main() {
cin >> n >> q;
for (int i = 1; i <= n; i++)
cin >> arr[i];
while (q--) {
int op, x, y;
cin >> op >> x >> y;
if (op == 1)
arr[x] = y;
else {
if (x == y && arr[x] < 0)
cout << 1 << endl;
else {
if (y - x + 1 > 61)
cout << "Too large" << endl;
else {
int cnt = 0;
for (int i = x; i <= y; i++)
if (arr[i] < 0)
cnt++;
if (cnt % 2 == 0) {
ll res = 1;
for (int i = x; i <= y && res <= inf; i++)
res *= abs(arr[i]);
if (res > inf)
cout << "Too large" << endl;
else
cout << res << endl;
} else {
int l = x, r = y;
while (arr[l] > 0 && l <= y)
l++;
while (arr[r] > 0 && r >= x)
r--;
ll res1 = 1, res2 = 1;
for (int i = l + 1; i <= y && res1 <= inf; i++)
res1 *= abs(arr[i]);
for (int i = x; i < r && res2 <= inf; i++)
res2 *= abs(arr[i]);
if (res1 > inf || res2 > inf)
cout << "Too large" << endl;
else
cout << max(res1, res2) << endl;
}
}
}
}
}
return 0;
}

后续
接下来我会不断用C++来实现信奥比赛中的算法题、GESP考级编程题实现、白名单赛事考题实现,记录日常的编程生活、比赛心得,感兴趣的请关注,我后续将继续分享相关内容
更多推荐

所有评论(0)