Codeforces 1270G Subset with Zero Sum
Posted ljzalc1022
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Codeforces 1270G Subset with Zero Sum相关的知识,希望对你有一定的参考价值。
Codeforces 1270G Subset with Zero Sum
https://codeforces.com/contest/1270/problem/G
长度为 (n) 的正整数序列 (a_1,a_2,cdots,a_n) , 满足
[i - n le a_i le i - 1
]
请找出一个非空子序列满足和为 (0) .
可以证明总是存在合法方案.
有 (T) 组数据.
(1 le T le 10^6)
(1 le n le 10^6, sum n le 10^6)
Tutorial
将不等式变形
[1 le i -a_i le n
]
可以建立一张 (n) 个点的有向图,从 (i) 向 (i-a_i) 连边.
那么图中一定存在一个有向环,找到任意一个这样的环,设其中的点为 (u_1,u_2,cdots,u_k) ,则有
[u_1-a_{u_1}=u_2 u_2-a_{u_2}=u_3 \cdots u_k-a_{u_k}=u_1
]
所以可以得到 (a_{u_1}+a_{u_2}+cdots+a_{u_k}=0) .
复杂度 (O(n))
Code
#include <cassert>
#include <cstdio>
#include <iostream>
#include <vector>
#define debug(...) fprintf(stderr,__VA_ARGS__)
using namespace std;
inline char nc()
{
// return getchar();
static char buf[100000],*l=buf,*r=buf;
return l==r&&(r=(l=buf)+fread(buf,1,100000,stdin),l==r)?EOF:*l++;
}
template<class T> void read(T &x)
{
x=0; int f=1,ch=nc();
while(ch<‘0‘||ch>‘9‘){if(ch==‘-‘)f=-1;ch=nc();}
while(ch>=‘0‘&&ch<=‘9‘){x=x*10-‘0‘+ch;ch=nc();}
x*=f;
}
typedef long long ll;
const int maxn=1e6+50;
int n;
int T;
int a[maxn];
bool vis[maxn];
vector<int> R;
vector<int> an;
void dfs(int u)
{
if(vis[u]) return; vis[u]=1;
R.push_back(u);
dfs(u-a[u]);
}
int main()
{
read(T);
for(int kase=1;kase<=T;++kase)
{
read(n);
for(int i=1;i<=n;++i)
{
read(a[i]);
}
dfs(1);
ll sum=0;
for(int i=R.size()-1;~i;--i)
{
sum+=a[R[i]]; an.push_back(R[i]);
if(sum==0) break;
}
printf("%d
",(int)an.size());
for(int i=0;i<an.size();++i)
{
if(i) printf(" ");
printf("%d",an[i]);
}
printf("
");
R.clear();
an.clear();
for(int i=1;i<=n;++i) vis[i]=0;
}
return 0;
}
以上是关于Codeforces 1270G Subset with Zero Sum的主要内容,如果未能解决你的问题,请参考以下文章
Codeforces 837D - Round Subset DP
Codeforces 837D Round Subset - 动态规划 - 数论
D - Round Subset codeforces837d