题目链接:左右

Description

给你一个s数组,一个t数组,你可以对s数组执行以下两种操作

L 操作:每个数等于其左边的数加上自己

R 操作:每个数等于其右边的数加上自己

第一个数的左边是最后一个数,最后一个数的右边是第一个数

对于每个操作,所有的加法是同时进行的,即(new)s[i] = (old)s[i - 1] + (old)s[i]

现在问你s数组能否变成t数组。

数据范围 \(1\le n\le 50, 1\le s_i, t_i\le 10^{15}\)

Solution

引理:只要确定了\(L\)和\(R\)的次数,无论按什么顺序操作,最终序列都相同。

我们将这个数列视为一个多项式,并以\(0,1,...,n-1\)作为下标,则:

序列为\(a_0,a_1x,a_2x^2,...,a_{n-1}x^{n-1}\)

\(L\)操作等价于这个式子乘以\((1+x)\),指数对\(n\)取模。

\(R\)操作等价于这个式子乘以\((1+x^{n-1})\),指数对\(n\)取模。

我们发现,\(L\)和\(R\)操作的顺序并不影响序列的结果。

那么我们可以暴力枚举\(L\)和\(R\)的次数,并且直接模拟即可。

注意到,因为上限是\(10^{15}\),所以最多只需要\(L\)和\(R\)操作\(log\)次即可。

复杂度 \(O(n^3)\),跑不满。

Code

// Author: wlzhouzhuan
#pragma GCC optimize(2)
#pragma GCC optimize(3)
#include <bits/stdc++.h>
using namespace std; #define ll long long
#define ull unsigned long long
#define rint register int
#define rep(i, l, r) for (rint i = l; i <= r; i++)
#define per(i, l, r) for (rint i = l; i >= r; i--)
#define mset(s, _) memset(s, _, sizeof(s))
#define pb push_back
#define pii pair <int, int>
#define mp(a, b) make_pair(a, b) inline int read() {
int x = 0, neg = 1; char op = getchar();
while (!isdigit(op)) { if (op == '-') neg = -1; op = getchar(); }
while (isdigit(op)) { x = 10 * x + op - '0'; op = getchar(); }
return neg * x;
}
inline void print(int x) {
if (x < 0) { putchar('-'); x = -x; }
if (x >= 10) print(x / 10);
putchar(x % 10 + '0');
} const int N = 102;
ll a[N], b[N], n;
ll c[N], d[N]; bool check() {
for (int i = 1; i <= n; i++) if (c[i] != b[i]) return 0;
return 1;
}
int main() {
cin >> n;
for (int i = 1; i <= n; i++) cin >> a[i];
for (int i = 1; i <= n; i++) cin >> b[i];
for (int a1 = 0; a1 <= 50; a1++) {
for (int i = 1; i <= n; i++) c[i] = a[i];
int ok = 1;
for (int k = 1; k <= a1; k++) {
for (int i = 1; i <= n; i++) d[i] = c[i] + c[i == 1 ? n : i - 1];
for (int i = 1; i <= n; i++) {
c[i] = d[i];
if (c[i] > b[i]) {
ok = 0;
break;
}
}
}
if (!ok) continue;
int a2 = 50;
while (a2--) {
if (check()) {
puts("Yes");
exit(0);
}
for (int i = 1; i <= n; i++) d[i] = c[i] + c[i == n ? 1 : i + 1];
for (int i = 1; i <= n; i++) {
c[i] = d[i];
if (c[i] > b[i]) {
break;
}
}
}
}
puts("No");
return 0;
}

[XJOI3529] 左右的更多相关文章

随机推荐

  1. 软件构造实验-百度图像识别api

    识别结果: 识别结果:

  2. 什么是静态内部(Static Inner)类,语法要注意什么?

    4静态内部类(Static Inner Classes) 马克-to-win:这里的内部类的static,意思是它可以不用实例化外部类,就自己单独被实例化,单独存在(有点像生活中的办公室和办公桌(独立 ...

  3. Java 请求转发和重定向的区别以及JavaWeb三大作用域

    三大作用域以及转发和重定向 学习总结 1. 转发和重定向 转发 重定向 转发和重定向的区别: 什么时候用转发什么时候用重定向 三大作用域 作用域类型 作用域方法 如何选择作用域 总结 学习总结 1. ...

  4. c++对c的拓展_指针的引用

    套用引用公式:Type & ref =val; 假设:type 类型为int * 由公式得 int * & ref = val; // int * *const ref=&va ...

  5. JS正则表达式学习记录

    JS:正则表达式学习记录 <!DOCTYPE html> <html lang="en"> <head> <meta charset=&q ...

  6. python---从尾到头打印链表

    class ListNode: def __init__(self, x): self.val = x self.next = None class Solution: # 返回从尾部到头部的列表值序 ...

  7. redis集群在线迁移第一篇(数据在线迁移至新集群)实战一

    迁移背景:1.原来redis集群在A机房,需要把其迁移到新机房B上来.2.保证现有环境稳定.3.采用在线迁移方式,因为原有redis集群内有大量数据.4.如果是一个全新的redis集群搭建会简单很多. ...

  8. pip:带你认识一个 Python 开发工作流程中的重要工具

    摘要:许多Python项目使用pip包管理器来管理它们的依赖项.它包含在Python安装程序中,是Python中依赖项管理的重要工具. 本文分享自华为云社区<使用Python的pip管理项目的依 ...

  9. python中字符串、列表访问

    一.列表 列表由一系列按特定顺序排列的多个元素或空元素组成,包含字母表中所有字母.数字0~9或所有家庭成员姓名的列表:列表中各元素间可以没有任何关系:实际使用过程中,通常给列表指定一个表示复数的名称, ...

  10. 别像弱智一样提问 Stop-Ask-Questions-The-Stupid-Ways

    https://github.com/xcr1234/Stop-Ask-Questions-The-Stupid-Ways 你真的准备好了吗? 感谢群友 for you 提供 避免 xy-proble ...