A题,因为数据范围很小,所以只要暴力即可,如果能相遇一定范围不大,如果范围很大还没相遇一定是不会相遇的了。正解应当是用扩展欧几里得计算这个方程的整数解,再想办法看看有没有正整数解才是。

  B题,只要看懂了题意,用map维护一下即可。真不知道题目给的n是干嘛用的。。

  C题,如果不存在loop的情况就用np态判断一下即可。现在存在loop正向dfs是不可以的,因为dfs的顺序会对结果造成影响。那么采用倒着搜索的方式,如果某点是必败的,那么到达这个点的点必然是必胜的,如果当前点是必胜的,那么父亲节点的计数减1(每个点的计数初始化为这个点可以走的方法数),如果该父亲节点的计数点为0了,说明其子节点都是必胜点,该点为必败点。不论是必胜点还是必败点,在得出这个点的性质后需要入队继续搜索,那么自始至终没有入队的点就是loop点了。实现完以后可以发现这个方式和拓扑排序有点类似。代码如下:

 #include <bits/stdc++.h>
#define t_mid (l+r>>1)
#define ls (o<<1)
#define rs (o<<1|1)
#define lson ls,l,t_mid
#define rson rs,t_mid+1,r
using namespace std;
const int N = + ;
typedef long long ll;
typedef pair<int,int> pii;
//typedef pair<ll, int> pli; int n;
vector<int> s[];
bool vis[N][];
int deg[N][];
int dp[N][];
struct node
{
int pos, turn, ans; // 1 : win, 0 : lose
};
void bfs()
{
queue<node> Q;
Q.push((node){, , });
Q.push((node){, , });
dp[][] = dp[][] = ;
vis[][] = vis[][] = ;
for(int i=;i<=n;i++) deg[i][] = s[].size();
for(int i=;i<=n;i++) deg[i][] = s[].size();
while(!Q.empty())
{
node temp = Q.front(); Q.pop();
int turn = temp.turn, pos = temp.pos, ans = temp.ans;
int befturn = !turn;
dp[pos][turn] = ans;
if(ans == )
{
for(int step : s[befturn])
{
int befpos = pos - step;
if(befpos <= ) befpos += n;
if(!vis[befpos][befturn])
{
vis[befpos][befturn] = ;
Q.push((node){befpos, befturn, });
}
}
}
else
{
for(int step : s[befturn])
{
int befpos = pos - step;
if(befpos <= ) befpos += n;
if(--deg[befpos][befturn] == && !vis[befpos][befturn])
{
vis[befpos][befturn] = ;
Q.push((node){befpos, befturn, });
}
}
}
}
} int main()
{
cin >> n;
int t; scanf("%d",&t);
while(t--)
{
int x; scanf("%d", &x);
s[].push_back(x);
}
sort(s[].begin(), s[].end());
scanf("%d",&t);
while(t--)
{
int x; scanf("%d", &x);
s[].push_back(x);
}
bfs();
for(int j=;j<;j++)
{
for(int i=;i<=n;i++)
{
if(!vis[i][j]) printf("Loop ");
else if(dp[i][j]) printf("Win ");
else printf("Lose ");
}
puts("");
}
return ;
}

C

  D题,1操作是u到v建边,2操作是u到[L, R]建边,3操作是[L, R]到u建边,1操作直接建边即可,2操作和3操作需要在线段树上建边,2操作需要在第一棵线段树上从父亲往子节点建权值为0的边,3操作在第二棵线段树上反过来即可。最后跑dij即可。需要注意的是,一棵线段树的空间是2N,因此总共的点数是N+2N*2=5N。要注意线段实际上是化为log个点再建边的。具体见代码:

 #include <bits/stdc++.h>
#define t_mid (l+r>>1)
#define ls (o<<1)
#define rs (o<<1|1)
#define lson ls,l,t_mid
#define rson rs,t_mid+1,r
using namespace std;
const int N = 1e5 + ;
const int V = N * ;
typedef long long ll;
typedef pair<int,int> pii;
typedef pair<ll,int> pli;
const ll inf = 0x3f3f3f3f3f3f3f3f; int n, m, s;
vector<pii> G[V];
void addEdge(int u,int v,int w)
{
G[u].push_back(pii(v, w));
}
int id[][N<<], idx;
void build(int o,int l,int r,int who)
{
id[who][o] = ++idx;
if(l == r)
{
if(who == ) addEdge(id[who][o], l, );
else addEdge(l, id[who][o], );
return ;
}
build(lson, who);
build(rson, who);
if(who == )
{
addEdge(id[who][o], id[who][ls], );
addEdge(id[who][o], id[who][rs], );
}
else
{
addEdge(id[who][ls], id[who][o], );
addEdge(id[who][rs], id[who][o], );
}
}
vector<int> vs;
void get(int o,int l,int r,int ql,int qr,int who)
{
if(l == ql && r == qr)
{
vs.push_back(id[who][o]);
return ;
}
if(qr <= t_mid) get(lson,ql,qr,who);
else if(ql > t_mid) get(rson,ql,qr,who);
else
{
get(lson,ql,t_mid,who);
get(rson,t_mid+,qr,who);
}
} ll d[V];
void dij(int s)
{
memset(d,0x3f,sizeof d);
d[s] = ;
priority_queue<pli,vector<pli>,greater<pli> > Q;
Q.push(pli(0LL, s));
while(!Q.empty())
{
pli p = Q.top(); Q.pop();
int u = p.second;
ll dis = p.first;
if(dis > d[u]) continue;
for(pii e : G[u])
{
int v = e.first, w = e.second;
if(d[u] + w < d[v])
{
d[v] = d[u] + w;
Q.push(pli(d[v], v));
}
}
}
} int main()
{
cin >> n >> m >> s;
idx = n;
build(,,n,);
build(,,n,);
while(m--)
{
int op; scanf("%d",&op);
if(op == )
{
int u, v, w; scanf("%d%d%d",&u,&v,&w);
addEdge(u, v, w);
}
else
{
vs.clear();
int u, l, r, w;
scanf("%d%d%d%d",&u,&l,&r,&w);
if(op == )
{
get(,,n,l,r,);
for(int v : vs) addEdge(u, v, w);
}
else
{
get(,,n,l,r,);
for(int v : vs) addEdge(v, u, w);
}
}
}
dij(s);
for(int i=;i<=n;i++)
{
if(d[i] == inf) d[i] = -;
printf("%I64d%c",d[i],i==n?'\n':' ');
}
return ;
}

D

  E题,利用主席树可以在log的时间内找出一段不同的数的个数,那么对于一个k,不断的二分+主席树来找到最右边的数字个数不超过k的范围,这个复杂度是两个log,再考虑到k是从1到n,对一个k每次至少跳k个单位的距离,那么总共需要进行这个两个log的操作的次数是n/1+n/2+...+n/n = ln(n)。那么总的时间复杂度是nlogloglog,TLE。那么正确的做法是二分+主席树可以利用类似与在线段树上的树上二分操作优化成一个log,每次去寻找右边第一个个数超过k的位置并跳过去,那么最终的复杂度是nloglog,可A。要注意的是这里主席数的节点要从右往左插入。具体见代码:

 #include <bits/stdc++.h>
#define t_mid (l+r>>1)
//#define ls (o<<1)
//#define rs (o<<1|1)
//#define lson ls,l,t_mid
//#define rson rs,t_mid+1,r
using namespace std;
const int N = 1e5 + ;
typedef long long ll;
typedef pair<int,int> pii; int pre[N],a[N],n,m,tot;
int rt[N*],sum[N*],ls[N*],rs[N*];
void build(int &o,int l,int r)
{
o = ++tot;
sum[o] = ;
if(l == r) return ;
build(ls[o],l,t_mid);
build(rs[o],t_mid+,r);
}
void update(int &o,int l,int r,int last,int pos,int dt)
{
o = ++tot;
sum[o] = sum[last];
ls[o] = ls[last];
rs[o] = rs[last];
if(l == r) {sum[o] += dt; return ;}
if(pos <= t_mid) update(ls[o],l,t_mid,ls[last],pos,dt);
else update(rs[o],t_mid+,r,rs[last],pos,dt);
sum[o] = sum[ls[o]] + sum[rs[o]];
}
int query(int o,int l,int r,int k) // return the first bu man zu de r
{
if(l == r) return l;
int cnt = sum[ls[o]];
if(cnt > k) return query(ls[o],l,t_mid,k);
else return query(rs[o],t_mid+,r,k-cnt);
}
int ans[N]; int main()
{
cin >> n;
memset(pre,-,sizeof pre);
for(int i=;i<=n;i++) scanf("%d",a+i);
build(rt[],,n+); // a[n+1] = 0, but all the ai is >= 1, so is different one
for(int i=n;i>=;i--)
{
int now = a[i];
if(pre[now] == -)
{
update(rt[i],,n+,rt[i+],i,);
}
else
{
int temp;
update(temp,,n+,rt[i+],pre[now],-);
update(rt[i],,n+,temp,i,);
}
pre[now] = i;
}
for(int k=;k<=n;k++)
{
int L = , res = ;
while(L <= n)
{
int pos = query(rt[L],,n+,k);
L = pos;
res++;
}
ans[k] = res;
}
for(int i=;i<=n;i++) printf("%d%c",ans[i],i==n?'\n':' ');
return ;
}

E

CodeForces 787 题解的更多相关文章

  1. codeforces#536题解

    CodeForces#536 A. Lunar New Year and Cross Counting Description: Lunar New Year is approaching, and ...

  2. codeforces 1093 题解

    12.18 update:补充了 $ F $ 题的题解 A 题: 题目保证一定有解,就可以考虑用 $ 2 $ 和 $ 3 $ 来凑出这个数 $ n $ 如果 $ n $ 是偶数,我们用 $ n / 2 ...

  3. Codeforces Numbers 题解

    这题只需要会10转P进制就行了. PS:答案需要约分,可以直接用c++自带函数__gcd(x,y). 洛谷网址 Codeforces网址 Code(C++): #include<bits/std ...

  4. Codeforces 691E题解 DP+矩阵快速幂

    题面 传送门:http://codeforces.com/problemset/problem/691/E E. Xor-sequences time limit per test3 seconds ...

  5. Codeforces 833B 题解(DP+线段树)

    题面 传送门:http://codeforces.com/problemset/problem/833/B B. The Bakery time limit per test2.5 seconds m ...

  6. Codeforces 840C 题解(DP+组合数学)

    题面 传送门:http://codeforces.com/problemset/problem/840/C C. On the Bench time limit per test2 seconds m ...

  7. Codeforces 515C 题解(贪心+数论)(思维题)

    题面 传送门:http://codeforces.com/problemset/problem/515/C Drazil is playing a math game with Varda. Let’ ...

  8. Codeforces 475D 题解(二分查找+ST表)

    题面: 传送门:http://codeforces.com/problemset/problem/475/D Given a sequence of integers a1, -, an and q ...

  9. CodeForces CF875C题解

    题解 非常有意思的\(2-SAT\)的题. 听学长讲完之后感觉确实容易想到\(2-SAT\),顺理成章. 显然,对于两个串,对咱们来说有意义的显然是两个串中第一个不同的数字.那么,我们假设两个串分别是 ...

随机推荐

  1. 关于Windows下的访问控制模型

    在探索Windows操作系统的过程中,发现很多有意思 的东西. Windows下的访问控制模型也是我在Github上浏览代码时,无意中发现的. 项目地址 https://github.com/Krut ...

  2. VBA Excel对象(十九)

    使用VBA进行编程时,用户将要处理的重要对象很少.下面是一些常见的对象 - 应用程序对象 工作簿对象 工作表对象 范围对象 应用程序对象 应用程序对象由以下部分组成 - 应用程序范围的设置和选项. 返 ...

  3. MySQL 启动、登录、退出和目录结构

    一.启动 MySQL 服务器启动方式有两种: (1)通过服务的方式自动启动 (2)手动启动的方式 1.windows 服务方式启动 操作步骤: 也可以在 cmd 窗口 输入 services.msc ...

  4. Python函数Day2

    一.函数补充 只有一个参数时,变量用argv 二.动态参数 为了拓展,对于传入的实参数量不固定,需要万能参数,即动态参数 *args **kwargs 在函数定义时,在 *args为位置参数,起聚合的 ...

  5. Django :中间 件与csrf

    一.中间件 什么是中间件 中间件有什么用 自定义中间件 中间件应用场景 二.csrf csrf token跨站请求伪造 一.中间件 1.什么是中间件 中间件顾名思义,是介于request与respon ...

  6. 开源框架---tensorflow c++ API 一个卡了很久的问题

    <开源框架---tensorflow c++ API 运行第一个“手写字的例子”> 中可以说明tensorflow c++ API是好用的,.......

  7. c++ 流对象之streambuf(可当做缓冲区使用)

    在C++ 中引入了流的概念,我们很方便的通过流来读写文本数据和二进制数据,那么流对象的数据究竟是怎么存储的呢,为了搞清这个问题,先来看一看c++ 的 io 体系: 由图可以看出,在stream 的实现 ...

  8. super关键字小结(构造方法的执行是不是一定会创建对象?)

    1.父类 public class Person { private String name = "李四"; private int age; public Person() { ...

  9. BZOJ 3601 一个人的数论 (拉格朗日插值+莫比乌斯反演)

    题意 略 题解 orz Freopen的博客 CODE #pragma GCC optimize (3) #include <bits/stdc++.h> using namespace ...

  10. TDOA基础之 delayed tx 实现说明

    不论是在TWR 还是TDOA定位算法中,delayed tx 都会用到,这篇博文主要解析delayed tx 实现. 何为delayed tx? delayed tx 是延时发送,为何要延时?因为这个 ...