浙南联合训练赛20180318
英语水平大考验
B - Worms
It is lunch time for Mole. His friend, Marmot, prepared him a nice game for lunch.
Marmot brought Mole n ordered piles of worms such that i-th pile contains ai worms. He labeled all these worms with consecutive integers: worms in first pile are labeled with numbers 1 to a1, worms in second pile are labeled with numbers a1 + 1 to a1 + a2 and so on. See the example for a better understanding.
Mole can't eat all the worms (Marmot brought a lot) and, as we all know, Mole is blind, so Marmot tells him the labels of the best juicy worms. Marmot will only give Mole a worm if Mole says correctly in which pile this worm is contained.
Poor Mole asks for your help. For all juicy worms said by Marmot, tell Mole the correct answers.
Input
The first line contains a single integer n (1 ≤ n ≤ 105), the number of piles.
The second line contains n integers a1, a2, ..., an (1 ≤ ai ≤ 103, a1 + a2 + ... + an ≤ 106), where ai is the number of worms in the i-th pile.
The third line contains single integer m (1 ≤ m ≤ 105), the number of juicy worms said by Marmot.
The fourth line contains m integers q1, q2, ..., qm (1 ≤ qi ≤ a1 + a2 + ... + an), the labels of the juicy worms.
Output
Print m lines to the standard output. The i-th line should contain an integer, representing the number of the pile where the worm labeled with the number qi is.
Example
5
2 7 3 4 9
3
1 25 11
1
5
3
Note
For the sample input:
- The worms with labels from [1, 2] are in the first pile.
- The worms with labels from [3, 9] are in the second pile.
- The worms with labels from [10, 12] are in the third pile.
- The worms with labels from [13, 16] are in the fourth pile.
- The worms with labels from [17, 25] are in the fifth pile.
就是给你的集合的前面让你二分的,本来给你的就是前缀和的公式
#include <bits/stdc++.h> using namespace std; const int N=1e5+5; int a[N]; int main() { int n,q; cin>>n; a[0]=1; for(int i=1,x;i<=n;i++) cin>>x,a[i]=a[i-1]+x; cin>>q; for(int i=1,x;i<=q;i++) { cin>>x; int pos=lower_bound(a,a+n+1,x)-a; if(a[pos]==x)pos++; cout<<pos<<"\n"; } }
C - Ice Skating
Bajtek is learning to skate on ice. He's a beginner, so his only mode of transportation is pushing off from a snow drift to the north, east, south or west and sliding until he lands in another snow drift. He has noticed that in this way it's impossible to get from some snow drifts to some other by any sequence of moves. He now wants to heap up some additional snow drifts, so that he can get from any snow drift to any other one. He asked you to find the minimal number of snow drifts that need to be created.
We assume that Bajtek can only heap up snow drifts at integer coordinates.
Input
The first line of input contains a single integer n (1 ≤ n ≤ 100) — the number of snow drifts. Each of the following n lines contains two integers xi and yi (1 ≤ xi, yi ≤ 1000) — the coordinates of the i-th snow drift.
Note that the north direction coinсides with the direction of Oy axis, so the east direction coinсides with the direction of the Ox axis. All snow drift's locations are distinct.
Output
Output the minimal number of snow drifts that need to be created in order for Bajtek to be able to reach any snow drift from any other one.
Example
2
2 1
1 2
1
2
2 1
4 1
0
这个题目完全是读题的锅
若两个雪堆之间横坐标或纵坐标相同则建立一条边连接两个雪堆,也就是求一下联通块
Bajtek to be able to reach any snow drift from any other one.
#include<bits/stdc++.h> using namespace std; int X[105],Y[105],vis[105],n; void dfs(int j) { vis[j]=1; for(int i=0; i<n; i++) if(vis[i]==0&&(X[j]==X[i]||Y[j]==Y[i]))dfs(i); } int main() { cin>>n; for(int i=0; i<n; i++) cin>>X[i]>>Y[i]; int ans=-1; for(int i=0; i<n; i++) if(!vis[i])ans++,dfs(i); cout<<ans; }
D - The Two Routes
In Absurdistan, there are n towns (numbered 1 through n) and m bidirectional railways. There is also an absurdly simple road network — for each pair of different towns x and y, there is a bidirectional road between towns x and y if and only if there is no railway between them. Travelling to a different town using one railway or one road always takes exactly one hour.
A train and a bus leave town 1 at the same time. They both have the same destination, town n, and don't make any stops on the way (but they can wait in town n). The train can move only along railways and the bus can move only along roads.
You've been asked to plan out routes for the vehicles; each route can use any road/railway multiple times. One of the most important aspects to consider is safety — in order to avoid accidents at railway crossings, the train and the bus must not arrive at the same town (except town n) simultaneously.
Under these constraints, what is the minimum number of hours needed for both vehicles to reach town n (the maximum of arrival times of the bus and the train)? Note, that bus and train are not required to arrive to the town n at the same moment of time, but are allowed to do so.
Input
The first line of the input contains two integers n and m (2 ≤ n ≤ 400, 0 ≤ m ≤ n(n - 1) / 2) — the number of towns and the number of railways respectively.
Each of the next m lines contains two integers u and v, denoting a railway between towns u and v (1 ≤ u, v ≤ n, u ≠ v).
You may assume that there is at most one railway connecting any two towns.
Output
Output one integer — the smallest possible time of the later vehicle's arrival in town n. If it's impossible for at least one of the vehicles to reach town n, output - 1.
Example
4 2
1 3
3 4
2
4 6
1 2
1 3
1 4
2 3
2 4
3 4
-1
5 5
4 2
3 5
4 5
5 1
1 2
3
Note
In the first sample, the train can take the route and the bus can take the route
. Note that they can arrive at town 4 at the same time.
In the second sample, Absurdistan is ruled by railwaymen. There are no roads, so there's no way for the bus to reach town 4.
就是要1-n的最短路
经过很久的分析,得到一个想法,就是存在1-n的最短路,如果不存在就是求一下反图的最短路,不存在的就是求当前图的最短路
因为不允许两个同时到一个点,那么另一条就是直接到就行了啊
#include <bits/stdc++.h> using namespace std; const int N=405; int n,m,vis[N][N],d[N]; int bfs(int f) { fill(d,d+n+1,-1); queue<int>Q; Q.push(1),d[1]=0; while(!Q.empty()) { int x=Q.front(); Q.pop(); for(int i=1;i<=n;i++) if(vis[x][i]==f&&d[i]==-1)d[i]=d[x]+1,Q.push(i); } return d[n]; } int main() { scanf("%d%d",&n,&m); for(int i=0,u,v; i<m; i++) scanf("%d%d",&u,&v),vis[u][v]=vis[v][u]=1; cout<<bfs(1-vis[1][n]); return 0; }
E - Minimum Difficulty
Mike is trying rock climbing but he is awful at it.
There are n holds on the wall, i-th hold is at height ai off the ground. Besides, let the sequence ai increase, that is, ai < ai + 1 for all i from 1 to n - 1; we will call such sequence a track. Mike thinks that the track a1, ..., an has difficulty . In other words, difficulty equals the maximum distance between two holds that are adjacent in height.
Today Mike decided to cover the track with holds hanging on heights a1, ..., an. To make the problem harder, Mike decided to remove one hold, that is, remove one element of the sequence (for example, if we take the sequence (1, 2, 3, 4, 5) and remove the third element from it, we obtain the sequence (1, 2, 4, 5)). However, as Mike is awful at climbing, he wants the final difficulty (i.e. the maximum difference of heights between adjacent holds after removing the hold) to be as small as possible among all possible options of removing a hold. The first and last holds must stay at their positions.
Help Mike determine the minimum difficulty of the track after removing one hold.
Input
The first line contains a single integer n (3 ≤ n ≤ 100) — the number of holds.
The next line contains n space-separated integers ai (1 ≤ ai ≤ 1000), where ai is the height where the hold number i hangs. The sequence ai is increasing (i.e. each element except for the first one is strictly larger than the previous one).
Output
Print a single number — the minimum difficulty of the track after removing a single hold.
Example
3
1 4 6
5
5
1 2 3 4 5
2
5
1 2 3 7 8
4
Note
In the first sample you can remove only the second hold, then the sequence looks like (1, 6), the maximum difference of the neighboring elements equals 5.
In the second test after removing every hold the difficulty equals 2.
In the third test you can obtain sequences (1, 3, 7, 8), (1, 2, 7, 8), (1, 2, 3, 8), for which the difficulty is 4, 5 and 5, respectively. Thus, after removing the second element we obtain the optimal answer — 4.
去掉一个后的两两差的最小值的最大值
枚举去掉的那一个
#include<bits/stdc++.h> using namespace std; int a[105]; int main() { int n; cin>>n; for(int i=0; i<n; i++)cin>>a[i]; int t=1e9; for(int i=1; i<n-1; i++) { int ma=0; for(int j=1; j<n; j++) if(j==i)continue; else if(j==i+1&&j!=1&&a[j]-a[j-2]>ma)ma=a[j]-a[j-2]; else if(a[j]-a[j-1]>ma)ma=a[j]-a[j-1]; if(ma<t)t=ma; } cout<<t; }
F - k-Tree
Quite recently a creative student Lesha had a lecture on trees. After the lecture Lesha was inspired and came up with the tree of his own which he called a k-tree.
A k-tree is an infinite rooted tree where:
- each vertex has exactly k children;
- each edge has some weight;
- if we look at the edges that goes from some vertex to its children (exactly kedges), then their weights will equal 1, 2, 3, ..., k.
The picture below shows a part of a 3-tree.
As soon as Dima, a good friend of Lesha, found out about the tree, he immediately wondered: "How many paths of total weight n (the sum of all weights of the edges in the path) are there, starting from the root of a k-tree and also containing at least one edge of weight at least d?".
Help Dima find an answer to his question. As the number of ways can be rather large, print it modulo 1000000007 (109 + 7).
Input
A single line contains three space-separated integers: n, k and d (1 ≤ n, k ≤ 100; 1 ≤ d ≤ k).
Output
Print a single integer — the answer to the problem modulo 1000000007 (109 + 7).
Example
3 3 2
3
3 3 3
1
4 3 2
6
4 5 2
7
英语差翻译不出来
#include<bits/stdc++.h> using namespace std; const int MD=1e9+7; int dp[105],can[105]; int main() { int n,k,d; can[0]=1; cin>>n>>k>>d; for(int i=1;i<=n;i++) for(int j=1;j<=k&&i>=j;j++) can[i]=(can[i]+can[i-j])%MD;; for(int i=d;i<=n;i++) { for(int j=1;j<d;j++) dp[i]=(dp[i]+dp[i-j])%MD; for(int j=d;j<=k&&i>=j;j++) dp[i]=(dp[i]+can[i-j])%MD; } cout<<dp[n]; return 0; }
G - Cards
There are n cards (n is even) in the deck. Each card has a positive integer written on it. n / 2 people will play new card game. At the beginning of the game each player gets two cards, each card is given to exactly one player.
Find the way to distribute cards such that the sum of values written of the cards will be equal for each player. It is guaranteed that it is always possible.
Input
The first line of the input contains integer n (2 ≤ n ≤ 100) — the number of cards in the deck. It is guaranteed that n is even.
The second line contains the sequence of n positive integers a1, a2, ..., an (1 ≤ ai ≤ 100), where ai is equal to the number written on the i-th card.
Output
Print n / 2 pairs of integers, the i-th pair denote the cards that should be given to the i-th player. Each card should be given to exactly one player. Cards are numbered in the order they appear in the input.
It is guaranteed that solution exists. If there are several correct answers, you are allowed to print any of them.
Example
6
1 5 7 4 4 3
1 3
6 2
4 5
4
10 10 10 10
1 2
3 4
Note
In the first sample, cards are distributed in such a way that each player has the sum of numbers written on his cards equal to 8.
In the second sample, all values ai are equal. Thus, any distribution is acceptable.
每次都扫一遍取最大最小
#include <iostream> #include <algorithm> using namespace std; bool vis[101]={0}; int a[101]; int main() { int n; cin>>n; for(int i=0;i<n;i++) cin>>a[i]; for(int i=0;i<n/2;i++) { int ma=0,maf=0,mi=101,mif=0; for(int j=0;j<n;j++) { if(!vis[j]&&a[j]<mi) mi=a[j],mif=j; } vis[mif]=1; for(int j=0;j<n;j++) { if(!vis[j]&&a[j]>ma) ma=a[j],maf=j; } vis[maf]=1; cout<<mif+1<<' '<<maf+1<<endl; } }
学弟这个复杂度更低
#include<bits/stdc++.h> using namespace std; #define pii pair<int,int> vector<pii> v; int main() { int n,a; cin>>n; for(int i=1;i<=n;i++) { cin>>a; v.push_back(pii(a,i)); } sort(v.begin(),v.end()); int i=0,j=n-1; while(i<=j) cout<<v[i++].second<<' '<<v[j--].second<<endl; return 0; }
H - Mashmokh and ACM
Mashmokh's boss, Bimokh, didn't like Mashmokh. So he fired him. Mashmokh decided to go to university and participate in ACM instead of finding a new job. He wants to become a member of Bamokh's team. In order to join he was given some programming tasks and one week to solve them. Mashmokh is not a very experienced programmer. Actually he is not a programmer at all. So he wasn't able to solve them. That's why he asked you to help him with these tasks. One of these tasks is the following.
A sequence of l integers b1, b2, ..., bl (1 ≤ b1 ≤ b2 ≤ ... ≤ bl ≤ n) is called good if each number divides (without a remainder) by the next number in the sequence. More formally for all i (1 ≤ i ≤ l - 1).
Given n and k find the number of good sequences of length k. As the answer can be rather large print it modulo 1000000007 (109 + 7).
Input
The first line of input contains two space-separated integers n, k (1 ≤ n, k ≤ 2000).
Output
Output a single integer — the number of good sequences of length k modulo 1000000007 (109 + 7).
Example
3 2
5
6 4
39
2 1
2
Note
In the first sample the good sequences are: [1, 1], [2, 2], [3, 3], [1, 2], [1, 3].
上次ZOJ月赛的原题,埃筛然后去枚举下最后一个数
#include<bits/stdc++.h> using namespace std; typedef long long ll; const ll MD=1e9+7; const int N=2005; ll dp[N][N]; int main() { int n,k; cin>>n>>k; memset(dp,0,sizeof dp); for(int i=1; i<N; i++) dp[1][i]=1; for(int i=1; i<k; i++) for(int j=1; j<=n; j++) for(int s=1; s*j<=n; s++) dp[i+1][s*j]=(dp[i+1][s*j]+dp[i][j])%MD; ll sum=0; for(int i=1; i<=n; i++) sum=(sum+dp[k][i])%MD; cout<<(sum+MD)%MD<<endl; return 0; }
I - Maze
Pavel loves grid mazes. A grid maze is an n × m rectangle maze where each cell is either empty, or is a wall. You can go from one cell to another only if both cells are empty and have a common side.
Pavel drew a grid maze with all empty cells forming a connected area. That is, you can go from any empty cell to any other one. Pavel doesn't like it when his maze has too little walls. He wants to turn exactly k empty cells into walls so that all the remaining cells still formed a connected area. Help him.
Input
The first line contains three integers n, m, k (1 ≤ n, m ≤ 500, 0 ≤ k < s), where nand m are the maze's height and width, correspondingly, k is the number of walls Pavel wants to add and letter s represents the number of empty cells in the original maze.
Each of the next n lines contains m characters. They describe the original maze. If a character on a line equals ".", then the corresponding cell is empty and if the character equals "#", then the cell is a wall.
Output
Print n lines containing m characters each: the new maze that fits Pavel's requirements. Mark the empty cells that you transformed into walls as "X", the other cells must be left without changes (that is, "." and "#").
It is guaranteed that a solution exists. If there are multiple solutions you can output any of them.
Example
3 4 2
#..#
..#.
#...
#.X#
X.#.
#...
5 4 5
#...
#.#.
.#..
...#
.#.#
#XXX
#X#.
X#..
...#
.#.#
.形成一个联通块,然后让你覆盖k个,还是联通块
那你就优先选择覆盖小的,然后最大的这一块你的选择就是填边角的,也就是这是最后一层bfs到的
#include<bits/stdc++.h> using namespace std; #define pii pair<int,int> const int N=500+5,M=N*N; struct p { int x,y,num; }S[M]; bool cmp(p a,p b) { return a.num>b.num; } int cnt=0,n,m,k; int Vis[N][N]; char G[N][N]; int dx[]={1,-1,0,0}; int dy[]={0,0,1,-1}; int bfs(int x,int y) { int num=1; p h,t; h.x=x;h.y=y; queue<p> Q; Q.push(h); while(!Q.empty()) { h=Q.front();Q.pop(); for(int i=0;i<4;i++) { t.x=h.x+dx[i]; t.y=h.y+dy[i]; if(t.x>=0&&t.x<n&&t.y>=0&&t.y<m&&Vis[t.x][t.y]==0&&G[t.x][t.y]=='.') { Vis[t.x][t.y]=1; Q.push(t); num++; } } } return num; } void bfs1(int x,int y) { p h,t; h.x=x;h.y=y; queue<p> Q; Q.push(h); while(!Q.empty()) { h=Q.front();Q.pop(); for(int i=0;i<4;i++) { t.x=h.x+dx[i]; t.y=h.y+dy[i]; if(t.x>=0&&t.x<n&&t.y>=0&&t.y<m&&G[t.x][t.y]=='.') { G[t.x][t.y]='X'; k--; Q.push(t); } } } } void dfs(int x,int y) { Vis[x][y]=1; if(k>0) { for(int i=0;i<4;i++) { int xx=x+dx[i]; int yy=y+dy[i]; if(xx>=0&&xx<n&&yy>=0&&yy<m&&G[xx][yy]=='.'&&Vis[xx][yy]==0) dfs(xx,yy); } if(k>0) { G[x][y]='X'; k--; } } } int main() { cin>>n>>m>>k; for(int i=0;i<n;i++) scanf("%s",G[i]); for(int i=0;i<n;i++) { for(int j=0;j<m;j++) { if(G[i][j]=='.'&&Vis[i][j]==0) { Vis[i][j]=1; S[cnt].x=i; S[cnt].y=j; S[cnt++].num=bfs(i,j); } } } sort(S,S+cnt,cmp); for(int i=1;i<cnt;i++) bfs1(S[i].x,S[i].y);//XXXX if(k>0) { memset(Vis,0,sizeof(Vis)); dfs(S[0].x,S[0].y); } for(int i=0;i<n;i++) printf("%s\n",G[i]); return 0; }
J - Lakes in Berland
The map of Berland is a rectangle of the size n × m, which consists of cells of size 1 × 1. Each cell is either land or water. The map is surrounded by the ocean.
Lakes are the maximal regions of water cells, connected by sides, which are not connected with the ocean. Formally, lake is a set of water cells, such that it's possible to get from any cell of the set to any other without leaving the set and moving only to cells adjacent by the side, none of them is located on the border of the rectangle, and it's impossible to add one more water cell to the set such that it will be connected with any other cell.
You task is to fill up with the earth the minimum number of water cells so that there will be exactly k lakes in Berland. Note that the initial number of lakes on the map is not less than k.
Input
The first line of the input contains three integers n, m and k (1 ≤ n, m ≤ 50, 0 ≤ k ≤ 50) — the sizes of the map and the number of lakes which should be left on the map.
The next n lines contain m characters each — the description of the map. Each of the characters is either '.' (it means that the corresponding cell is water) or '*' (it means that the corresponding cell is land).
It is guaranteed that the map contain at least k lakes.
Output
In the first line print the minimum number of cells which should be transformed from water to land.
In the next n lines print m symbols — the map after the changes. The format must strictly follow the format of the map in the input data (there is no need to print the size of the map). If there are several answers, print any of them.
It is guaranteed that the answer exists on the given data.
Example
5 4 1
****
*..*
****
**.*
..**
1
****
*..*
****
****
..**
3 3 0
***
*.*
***
1
***
***
***
Note
In the first example there are only two lakes — the first consists of the cells (2, 2) and (2, 3), the second consists of the cell (4, 3). It is profitable to cover the second lake because it is smaller. Pay attention that the area of water in the lower left corner is not a lake because this area share a border with the ocean.
这个题是上一题的减弱版,就是处理那个和海相连的还是要bfs完全的,我们改错了,卡了一大波时间
#include<bits/stdc++.h> using namespace std; #define pii pair<int,int> const int N=500; struct p { int x,y,num; }S[100000]; bool cmp(p a,p b) { return a.num<b.num; } int cnt,n,m,k; int Vis[N][N]; char G[N][N]; int dx[]={1,-1,0,0}; int dy[]={0,0,1,-1}; int bfs(int x,int y) { int num=1,f=1; p h,t; h.x=x;h.y=y; queue<p> Q; Q.push(h); while(!Q.empty()) { h=Q.front();Q.pop(); for(int i=0;i<4;i++) { t.x=h.x+dx[i]; t.y=h.y+dy[i]; if(t.x>=0&&t.x<n&&t.y>=0&&t.y<m&&Vis[t.x][t.y]==0&&G[t.x][t.y]=='.') { if(t.x==0||t.x==n-1||t.y==0||t.y==m-1)f=0; Vis[t.x][t.y]=1; Q.push(t); num++; } } } if(f) return num; return -1; } void bfs1(int x,int y) { G[x][y]='*'; p h,t; h.x=x;h.y=y; queue<p> Q; Q.push(h); while(!Q.empty()) { h=Q.front();Q.pop(); for(int i=0;i<4;i++) { t.x=h.x+dx[i]; t.y=h.y+dy[i]; if(t.x>=0&&t.x<n&&t.y>=0&&t.y<m&&G[t.x][t.y]=='.') { G[t.x][t.y]='*'; Q.push(t); } } } } int main() { cin>>n>>m>>k; for(int i=0;i<n;i++) scanf("%s",G[i]); for(int i=1;i<n-1;i++) { for(int j=1;j<m-1;j++) { if(G[i][j]=='.'&&Vis[i][j]==0) { Vis[i][j]=1; int num=bfs(i,j); if(num!=-1) { S[cnt].x=i; S[cnt].y=j; S[cnt++].num=num; } } } } sort(S,S+cnt,cmp); int ans=0; for(int i=0;i<cnt-k;i++) { ans+=S[i].num; bfs1(S[i].x,S[i].y); } printf("%d\n",ans); for(int i=0;i<n;i++) printf("%s\n",G[i]); return 0; }
L - Chat room
Vasya has recently learned to type and log on to the Internet. He immediately entered a chat room and decided to say hello to everybody. Vasya typed the word s. It is considered that Vasya managed to say hello if several letters can be deleted from the typed word so that it resulted in the word "hello". For example, if Vasya types the word "ahhellllloou", it will be considered that he said hello, and if he types "hlelo", it will be considered that Vasya got misunderstood and he didn't manage to say hello. Determine whether Vasya managed to say hello by the given word s.
Input
The first and only line contains the word s, which Vasya typed. This word consisits of small Latin letters, its length is no less that 1 and no more than 100 letters.
Output
If Vasya managed to say hello, print "YES", otherwise print "NO".
Example
ahhellllloou
YES
hlelo
NO
在一个串里找hello,双指针
#include <bits/stdc++.h> using namespace std; const int N=1e6+5; string s="hello"; string c; int main() { int f=0,j=0; cin>>c; for(int i=0;c[i]&&j!=5;i++) if(c[i]==s[j])j++; printf("%s\n",j==5?"YES":"NO"); }
A - Wet Shark and Blocks
There are b blocks of digits. Each one consisting of the same n digits, which are given to you in the input. Wet Shark must choose exactly one digit from each block and concatenate all of those digits together to form one large integer. For example, if he chooses digit 1 from the first block and digit 2 from the second block, he gets the integer 12.
Wet Shark then takes this number modulo x. Please, tell him how many ways he can choose one digit from each block so that he gets exactly k as the final result. As this number may be too large, print it modulo 109 + 7.
Note, that the number of ways to choose some digit in the block is equal to the number of it's occurrences. For example, there are 3 ways to choose digit 5 from block 3 5 6 7 8 9 5 1 1 1 1 5.
Input
The first line of the input contains four space-separated integers, n, b, k and x(2 ≤ n ≤ 50 000, 1 ≤ b ≤ 109, 0 ≤ k < x ≤ 100, x ≥ 2) — the number of digits in one block, the number of blocks, interesting remainder modulo x and modulo x itself.
The next line contains n space separated integers ai (1 ≤ ai ≤ 9), that give the digits contained in each block.
Output
Print the number of ways to pick exactly one digit from each blocks, such that the resulting integer equals k modulo x.
Example
12 1 5 10
3 5 6 7 8 9 5 1 1 1 1 5
3
3 2 1 2
6 2 2
0
3 2 1 2
3 1 2
6
Note
In the second sample possible integers are 22, 26, 62 and 66. None of them gives the remainder 1 modulo 2.
In the third sample integers 11, 13, 21, 23, 31 and 33 have remainder 1 modulo 2. There is exactly one way to obtain each of these integers, so the total answer is 6.
有b组数,每组数均有n个相同。
你必须在每组选一个数,组成一个新数sum,使得sum % x == k,问方案数 % (1e9+7)。
一时间还真的想不到做法,这个题目数据量很大,大概是快速幂,可是这个怎么去处理啊
因为每一层的1-9的个数及种类是不变的,而且前面的数*10+本层的数%x是不变的 这个有点数论的意思
#include<bits/stdc++.h> using namespace std; const int N=5e4+5,MD=1e9+7; int a[105][105],v[N],f[105][105],t[105][105]; int n,b,k,m; void mul(int a[][105],int b[][105]) { memset(t,0,sizeof(t)); for(int i=0; i<m; i++) for(int j=0; j<m; j++) for(int l=0; l<m; l++) t[i][j]=(t[i][j]+a[i][l]*1LL*b[l][j]%MD)%MD; memcpy(a,t,sizeof(t)); } void pow(int a[][105],int n) { while(n) { if(n&1)mul(a,f); mul(f,f); n>>=1; } } int main() { cin>>n>>b>>k>>m; for(int i=1; i<=n; i++)cin>>v[i]; for(int i=0; i<m; i++) for(int j=1; j<=n; j++) f[(i*10+v[j])%m][i]++; for(int i=0; i<m; i++)a[i][i]=1; pow(a,b); printf("%d\n",a[k][0]); return 0; }
K - Nikita and stack
Nikita has a stack. A stack in this problem is a data structure that supports two operations. Operation push(x) puts an integer x on the top of the stack, and operation pop() deletes the top integer from the stack, i. e. the last added. If the stack is empty, then the operation pop() does nothing.
Nikita made m operations with the stack but forgot them. Now Nikita wants to remember them. He remembers them one by one, on the i-th step he remembers an operation he made pi-th. In other words, he remembers the operations in order of some permutation p1, p2, ..., pm. After each step Nikita wants to know what is the integer on the top of the stack after performing the operations he have already remembered, in the corresponding order. Help him!
Input
The first line contains the integer m (1 ≤ m ≤ 105) — the number of operations Nikita made.
The next m lines contain the operations Nikita remembers. The i-th line starts with two integers pi and ti(1 ≤ pi ≤ m, ti = 0 or ti = 1) — the index of operation he remembers on the step i, and the type of the operation. ti equals 0, if the operation is pop(), and 1, is the operation is push(x). If the operation is push(x), the line also contains the integer xi (1 ≤ xi ≤ 106) — the integer added to the stack.
It is guaranteed that each integer from 1 to m is present exactly once among integers pi.
Output
Print m integers. The integer i should equal the number on the top of the stack after performing all the operations Nikita remembered on the steps from 1 to i. If the stack is empty after performing all these operations, print -1.
Example
2
2 1 2
1 0
2
2
3
1 1 2
2 1 3
3 0
2
3
2
5
5 0
4 0
3 1 1
2 1 1
1 1 2
-1
-1
-1
-1
2
Note
In the first example, after Nikita remembers the operation on the first step, the operation push(2) is the only operation, so the answer is 2. After he remembers the operation pop() which was done before push(2), answer stays the same.
In the second example, the operations are push(2), push(3) and pop(). Nikita remembers them in the order they were performed.
In the third example Nikita remembers the operations in the reversed order.
我们把出栈操作看作-1,入栈操作看作+1,那么倒着数第一个使得操作为+的元素就是栈顶元素.
最靠右使得后缀和为1的有的数是多少
我的线段树一团糟,看了题解抄的
#include<bits/stdc++.h> using namespace std; const int N=1e5+5; int n,w[N]; struct T { int l,r,push,pop; } a[N*3]; void build(int l,int r,int tr) { a[tr].l=l,a[tr].r=r,a[tr].push=a[tr].pop=0; if(l==r)return; int mi=(l+r)>>1; build(l,mi,tr<<1); build(mi+1,r,tr<<1|1); } void change(int pos,int x,int tr) { if(a[tr].l==a[tr].r) { if(x) a[tr].push=1; else a[tr].pop=1; return; } int mi=(a[tr].l+a[tr].r)>>1; if(pos<=mi) change(pos,x,tr<<1); else change(pos,x,tr<<1|1); int f=min(a[tr<<1].push,a[tr<<1|1].pop); a[tr].push=a[tr<<1].push+a[tr<<1|1].push-f; a[tr].pop =a[tr<<1].pop +a[tr<<1|1].pop -f; } int query(int sum,int tr) { if(!a[tr].push) return -1; if(a[tr].l==a[tr].r) return w[a[tr].l]; int mi=(a[tr].l+a[tr].r)>>1; if(a[tr<<1|1].push+sum>0) return query(sum,tr<<1|1); else return query(sum+a[tr<<1|1].push-a[tr<<1|1].pop,tr<<1); } int main() { scanf("%d",&n); build(1,n,1); for(int i=1,pos,opt; i<=n; i++) { scanf("%d%d",&pos,&opt); if(opt==1)scanf("%d",&w[pos]); change(pos,opt,1); printf("%d\n",query(0,1)); } return 0; }
本文来自博客园,作者:暴力都不会的蒟蒻,转载请注明原文链接:https://www.cnblogs.com/BobHuang/p/8598808.html