昨天训练的题目,今天终于把题补完了。补完之后又忍不住骂了自己几句智障,感觉很不是状态。
然后立一个flag吧,之后所有的cf div2的题全部补完,不会的看题解补,为区域赛准备。今年作为coder之后压力还是比较大的,不过也是一个比较好的提高的机会吧,累并快乐着。
Anastasia loves going for a walk in Central Uzhlyandian Park. But she became uninterested in simple walking, so she began to collect Uzhlyandian pebbles. At first, she decided to collect all the pebbles she could find in the park.
She has only two pockets. She can put at most k pebbles in each pocket at the same time. There are n different pebble types in the park, and there are wi pebbles of the i-th type. Anastasia is very responsible, so she never mixes pebbles of different types in same pocket. However, she can put different kinds of pebbles in different pockets at the same time. Unfortunately, she can't spend all her time collecting pebbles, so she can collect pebbles from the park only once a day.
Help her to find the minimum number of days needed to collect all the pebbles of Uzhlyandian Central Park, taking into consideration that Anastasia can't place pebbles of different types in same pocket.
The first line contains two integers n and k (1 ≤ n ≤ 105, 1 ≤ k ≤ 109) — the number of different pebble types and number of pebbles Anastasia can place in one pocket.
The second line contains n integers w1, w2, ..., wn (1 ≤ wi ≤ 104) — number of pebbles of each type.
The only line of output contains one integer — the minimum number of days Anastasia needs to collect all the pebbles.
3 2 2 3 4
3
A题: 有n种石子,容量为k的口袋,每个口袋中不能放不同种类的石子,一天最多装两口袋,问最少几天装完。
对于所有的 a[i] 我们至少需要装a[i]/i+1次,对于所有的a[i]&1==1的石子需要多装一次,然后一天最多两次,end。
#include
using namespace std;
const int maxn = 1e5+5;
const double Pi = acos(-1.0);
const double eps = 1e-8;
int a[maxn];
int main()
{
cin.sync_with_stdio(false);
int n, k, sum=0;
cin>>n>>k;
for(int i=0; i>a[i];
sum += a[i]/k;
if(a[i]%k) sum++;
}
cout<<(sum+1)/2<
昨天刚学会的cin.sync_with_stdio(false)所以会一直在用,一个是为了加快自己的速度,另外一个是因为队友比较习惯用cin cout,大家编码习惯还是统一一点比较好,对于对时间要求较高的题目,还是推荐使用 scanf 或者 fastIO
Masha really loves algebra. On the last lesson, her strict teacher Dvastan gave she new exercise.
You are given geometric progression b defined by two integers b1 and q. Remind that a geometric progression is a sequence of integers b1, b2, b3, ..., where for each i > 1 the respective term satisfies the condition bi = bi - 1·q, where q is called the common ratio of the progression. Progressions in Uzhlyandia are unusual: both b1 and q can equal 0. Also, Dvastan gave Masha m "bad" integers a1, a2, ..., am, and an integer l.
Masha writes all progression terms one by one onto the board (including repetitive) while condition |bi| ≤ l is satisfied (|x| means absolute value of x). There is an exception: if a term equals one of the "bad" integers, Masha skips it (doesn't write onto the board) and moves forward to the next term.
But the lesson is going to end soon, so Masha has to calculate how many integers will be written on the board. In order not to get into depression, Masha asked you for help: help her calculate how many numbers she will write, or print "inf" in case she needs to write infinitely many integers.
The first line of input contains four integers b1, q, l, m (-109 ≤ b1, q ≤ 109, 1 ≤ l ≤ 109, 1 ≤ m ≤ 105) — the initial term and the common ratio of progression, absolute value of maximal number that can be written on the board and the number of "bad" integers, respectively.
The second line contains m distinct integers a1, a2, ..., am (-109 ≤ ai ≤ 109) — numbers that will never be written on the board.
Print the only integer, meaning the number of progression terms that will be written on the board if it is finite, or "inf" (without quotes) otherwise.
3 2 30 4 6 14 25 48
3
B题:给定数列第一项b1和公比q,绝对值的上界l以及m个hate的数字。要求顺序求出数列的各项,当任意一项绝对值大于l时停止,如果不是hate的数字就标记,问足够长的时间后,标记数字的个数。如果无限则输出inf
一开始想到的是,如果公比为0 1 -1则有可能出现无限的情况,其余情况就算是极限数据也是log级别的完全可以暴力出来。那么就分公比情况进行模拟,暴力求解。但是因为自己不细致+没有认真分情况一连WA了6发。然后决定转用multiset优化一发过了。
基本思路,如果一个数出现了10次以上,我们就可以认为出现循环了(其实3次就可以判循环,这里是随手写的)。不出现循环则我可以模拟暴力求解,出现循环时,如果我标记的数字个数大于1个,则是inf,否则的话照样输出标记计数。原因是因为可能会出现所有值都hate,或者第一个值不hate,公比q为0,0是hate。 End
#include
using namespace std;
const int maxn = 1e5+5;
const double Pi = acos(-1.0);
const double eps = 1e-8;
sets1;
multisets3, s2;
int abs(int x) { return x<0?-x:x;}
int main()
{
cin.sync_with_stdio(false);
long long n, q, l, m, sum=0;
bool inf = false;
cin>>n>>q>>l>>m;
for(int i=0; i>num;
s1.insert(num);
}
long long x = n;
while(abs(n)<=l)
{
if(!s1.count(n)) sum++;
if(s2.count(n)>=10) {
if(sum>1) inf = true;
break;
}
s2.insert(n);
n *= q;
}
// if(((q==0 && !s1.count(0)) || (q==1 && !s1.count(n)) || (q==-1 && (!s1.count(n) || !s1.count(-n)))) && abs(x)<=l) puts("inf");
if(inf) puts("inf");
else cout<
注释掉部分就是一开始模拟时候开的坑,到最后都没有模拟过去,膜拜所有昨天过题的大佬,我看了一眼都是模拟过得,代码能力maxx。
Something happened in Uzhlyandia again... There are riots on the streets... Famous Uzhlyandian superheroes Shean the Sheep and Stas the Giraffe were called in order to save the situation. Upon the arriving, they found that citizens are worried about maximum values of the Main Uzhlyandian Function f, which is defined as follows:
In the above formula, 1 ≤ l < r ≤ n must hold, where n is the size of the Main Uzhlyandian Array a, and |x| means absolute value of x. But the heroes skipped their math lessons in school, so they asked you for help. Help them calculate the maximum value of f among all possible values of l and r for the given array a.
The first line contains single integer n (2 ≤ n ≤ 105) — the size of the array a.
The second line contains n integers a1, a2, ..., an (-109 ≤ ai ≤ 109) — the array elements.
Print the only integer — the maximum value of f.
5 1 4 2 3 1
3
C题:给定一个数列,定义了一种运算f(l, r) ,对于任意对 (l, r) 我们可以得到一个函数值,问其中最大的是多少。
基本思路,对于一个给定的数列,求其连续区间的最大和,我们可以直接用dp去解,而这道题不同的地方在于,这个序列是不定的,通过对公式的分析我们发现,对于固定的位置,它取值的正负性只和l的奇偶性有关,那么我们可以根据l奇偶性的不同得到两个新的序列,然后对这两个序列进行dp。需要注意的是,因为我们的新序列是根据起点的奇偶性来的,所以我们最好使用倒序dp的方式,即从原来以某一位为结尾连续序列最大和的想法,转换为以某一位为起点,连续序列最大和。End
#include
#define LL long long
using namespace std;
const int maxn = 1e5+5;
const double Pi = acos(-1.0);
const double eps = 1e-8;
const int mod = 1e9+7;
const int INF = 0x3f3f3f3f;
//LL abs(LL x){return x<0?-x:x;}
LL a[maxn], b[maxn], c[maxn];
LL dp[maxn];
int main()
{
cin.sync_with_stdio(false);
int n;
LL ans = -mod;
cin>>n;
for(int i=0; i>a[i];
for(int i=1; i=1; i--)
{
if(i&1)
{
dp[i]=b[i];
if(i+2
Little boy Igor wants to become a traveller. At first, he decided to visit all the cities of his motherland — Uzhlyandia.
It is widely known that Uzhlyandia has n cities connected with m bidirectional roads. Also, there are no two roads in the country that connect the same pair of cities, but roads starting and ending in the same city can exist. Igor wants to plan his journey beforehand. Boy thinks a path is good if the path goes over m - 2 roads twice, and over the other 2 exactly once. The good path can start and finish in any city of Uzhlyandia.
Now he wants to know how many different good paths are in Uzhlyandia. Two paths are considered different if the sets of roads the paths goes over exactly once differ. Help Igor — calculate the number of good paths.
The first line contains two integers n, m (1 ≤ n, m ≤ 106) — the number of cities and roads in Uzhlyandia, respectively.
Each of the next m lines contains two integers u and v (1 ≤ u, v ≤ n) that mean that there is road between cities u and v.
It is guaranteed that no road will be given in the input twice. That also means that for every city there is no more than one road that connects the city to itself.
Print out the only integer — the number of good paths in Uzhlyandia.
5 4 1 2 1 3 1 4 1 5
6
D题:给定n个点m条边,m条边中,选择其中两条边只走一次,其余边走两次的连续走法有多少种。当只走一次的两边所组成的集合是不同的的时候,我们认为两种走法是不同的。
基本思路:这道题场上没有A出来,场下也是看了题解才懂,再次对场上A题大佬表示敬意。连续走法第一反应应该是欧拉路,而既然其余边要走两次,我们就直接给每条边加一个复制,然后选择其中两条边后判断是否满足欧拉路的条件: 奇点的个数为0个或两个. 那么我们现在讨论选择边对于奇点个数的影响.
1. 不相邻的两条普通边: 奇点数为4 不满足
2. 相邻的两条普通边: 奇点数为2 满足
3. 一条普通边和一条自环: 奇点数为2 满足
4. 两条自环: 奇点数为0 满足
那么我们就可以记录出所有我们需要的数据, 同一个顶点有多少条边, 一共有多少个自环, 然后直接求解.
#include
#define LL long long
using namespace std;
const int maxn = 1e6+5;
int pre[maxn], cnt[maxn];
int found(int x)
{
if(pre[x]==-1) {
pre[x] = x;
return x;
}
else if(pre[x] == x) return x;
return pre[x] = found(pre[x]);
}
void join(int x, int y)
{
int x1 = found(x);
int y1 = found(y);
if(x1==y1) return ;
else {
pre[x1] = y1;
return ;
}
}
int main()
{
cin.sync_with_stdio(false);
int n, m, loop=0, sum = 0;
memset(pre, -1, sizeof pre);
LL ans = 0;
cin>>n>>m;
while(m--)
{
int s, t;
cin>>s>>t;
if(s == t){
loop ++;
}
else {
cnt[s]++;
cnt[t]++;
sum++;
}
join(s, t);
}
int flag = 0;
for(int i=1; i<=n; i++){
//cout< 1) ;
else{
for(int i=1; i<=n; i++){
if(cnt[i]>=2) ans += (LL)cnt[i]*(cnt[i]-1)/2;
//cout<
这里我用了并查集来判连通性,用数组记录每边的度。需要注意的是,题目只限定走边不需要走完所有的定点,以及如果边组成了两个以上的连通块则一定不行,输出-1。
Sasha and Kolya decided to get drunk with Coke, again. This time they have k types of Coke. i-th type is characterised by its carbon dioxide concentration . Today, on the party in honour of Sergiy of Vancouver they decided to prepare a glass of Coke with carbon dioxide concentration . The drink should also be tasty, so the glass can contain only integer number of liters of each Coke type (some types can be not presented in the glass). Also, they want to minimize the total volume of Coke in the glass.
Carbon dioxide concentration is defined as the volume of carbone dioxide in the Coke divided by the total volume of Coke. When you mix two Cokes, the volume of carbon dioxide sums up, and the total volume of Coke sums up as well.
Help them, find the minimal natural number of liters needed to create a glass with carbon dioxide concentration . Assume that the friends have unlimited amount of each Coke type.
The first line contains two integers n, k (0 ≤ n ≤ 1000, 1 ≤ k ≤ 106) — carbon dioxide concentration the friends want and the number of Coke types.
The second line contains k integers a1, a2, ..., ak (0 ≤ ai ≤ 1000) — carbon dioxide concentration of each type of Coke. Some Coke types can have same concentration.
Print the minimal natural number of liter needed to prepare a glass with carbon dioxide concentration , or -1 if it is impossible.
400 4 100 300 450 500
2
E题: E题一开始没有敢切,但是仔细分析之后就会发现其实也是一个比较简单的题。题意,给出n个数,求从中最少选多少个数可以使得他们的平均数为k。
基本思路:对于若干数构造平均数为k的例子,我们可以预先对这n个数进行处理,为 a[i] = n-a[i] 这样处理的原因是我们可以将每个数对平均数的贡献记录下来,当这种贡献为0时即平均数为0 。这样处理的好处是,我们省去了计算平均数的步骤。然后我们就可以用一个set存下这些可能的贡献,然后进行bfs。
#include
using namespace std;
const int maxn = 1e6+5;
int a[maxn];
int vis[1005];
int n, k;
sets;
int bfs()
{
queueq;
q.push(0);
vis[0] = 0;
while(!q.empty())
{
int now = q.front();
q.pop();
//cout<<"**"<::iterator it=s.begin(); it!=s.end(); it++)
{
int next = now + *it;
if(next<0 || vis[next]) continue;
else{
if(next == 0) return vis[now]+1;
vis[next] = vis[now] + 1;
q.push(next);
}
}
}
return -1;
}
int main()
{
//freopen("in.txt", "r", stdin);
cin.sync_with_stdio(false);
s.clear();
cin>>k>>n;
for(int i=0; i>a[i];
s.insert(a[i] - k);
}
cout<
需要注意的是,这道题中的数均为整数,而贡献有正有负, 我们看可以只记录贡献为正的情况,bfs到0 (贡献为负开始到0只是这个过程的逆序),这样的好处是我们就可以用vis数组记录每一个状态的步数了。因为下标不可以是负的。然后这道题中的数据贡献只有可能是[-1000, 1000],中一个长度为1000的子区间。而m的数据范围却有1e6。所以我们用了set之后可以减少遍历所小号的时间。
End 争取补出所有div2