A. Circle of Students     

题目:https://codeforces.com/contest/1203/problem/A

题意:一堆人坐成一个环,问能否按逆时针或者顺时针正好是 1-n的顺序

思路:水题,把数组开两倍,或者标记当前位置都可以

#include<bits/stdc++.h>
#define maxn 100005
#define mod 1000000007
using namespace std;
typedef long long ll;
int a[maxn],n;
int main(){
int t;
scanf("%d",&t);
while(t--){
scanf("%d",&n);
for(int i=;i<=n;i++) scanf("%d",&a[i]);
int dex=;
for(int i=;i<=n;i++){
if(a[i]==){
dex=i;
break;
}
}
int flag=;
int k=dex;
int z=,num=;
while(num<n){
k++;
if(k==n+) k=;
if(a[k]!=z+) break;
num++;
z++;
}
if(num==n) flag=;
//printf("num=%d k=%d z=%d\n",num,k,z);
k=dex;
z=,num=;
while(num<n){
k--;
if(k==) k=n;
if(a[k]!=z+) break;
num++;
z++;
}
if(num==n) flag=;
if(flag) printf("YES\n");
else printf("NO\n");
}
}

B. Equal Rectangles

题目:https://codeforces.com/contest/1203/problem/B

题意:有4*n根木棍,现在问能否组成n个面积相等的矩形

思路:首先我们组成第一个矩形肯定是最小和最大,然后第二个是次小和次大.....所以我们对木棒排序,然后两个指针判是否可行即可

 #include<bits/stdc++.h>
#define maxn 100005
#define mod 1000000007
using namespace std;
typedef long long ll;
int a[maxn],n;
int main(){
int t;
scanf("%d",&t);
while(t--){
scanf("%d",&n);
n=*n;
for(int i=;i<=n;i++) scanf("%d",&a[i]);
sort(a+,a+n+);
int l=,r=n,z=a[]*a[n];
int flag=;
while(l<r){
if(a[l]!=a[l+]||a[r]!=a[r-]){
flag=;
break;
}
if(a[l]*a[r]!=z){
flag=;
break;
}
z=a[l]*a[r];
l+=;
r-=;
}
if(flag) printf("NO\n");
else printf("YES\n");
}
}

C. Common Divisors

题目:https://codeforces.com/contest/1203/problem/C

题意:有一个序列,现在求一个数x,这个x是序列所有数的约数,求这样的x的数量

思路:我们首先能求出最大公约数,然后其他约数必然是最大公约数的因子,所以我们求出最大公约数的因子数即可

#include<bits/stdc++.h>
#define maxn 400005
#define mod 1000000007
using namespace std;
typedef long long ll;
ll a[maxn],n;
int main(){
scanf("%I64d",&n);
for(ll i=;i<=n;i++){
scanf("%I64d",&a[i]);
}
if(n==){
ll sum=;
ll g=a[];
for(ll i=;i*i<=g;i++){
if(g%i==){
sum++;
if(i!=g/i) sum++;
}
}
cout<<sum;
return ;
}
ll g=__gcd(a[],a[]);
for(ll i=;i<=n;i++){
g=__gcd(g,a[i]);
}
ll sum=;
for(ll i=;i*i<=g;i++){
if(g%i==){
sum++;
if(i!=g/i) sum++;
}
}
cout<<sum;
return ;
}

D1+D2. Remove the Substring

题目:https://codeforces.com/contest/1203/problem/D2

题意:有两个串,你可以执行一次删除操作,删除一段连续的字符,删除完之后第二个串依然是第一个串的子序列,求最大的可以删除的字符数

思路:  这个其实我们枚举删除的一段字符是在第二个串的哪两个字符中间即可,特别的判断下一个整的序列的左边右边,当然一个串里面可能出现多次字符出现位置,因为我们要求最大所以我们直接求一个前缀,所有字符出现的第一次位置,一个后缀,所有字符出现的最后一次,这样就能保证中间差距尽量大,然后我们枚举删除的字符在哪两个之间求max即可

#include<bits/stdc++.h>
#define maxn 200005
#define mod 1000000007
using namespace std;
typedef long long ll;
char s1[maxn],s2[maxn];
ll b1[maxn],b2[maxn];
int main(){
cin>>s1>>s2;
ll len1=strlen(s1);
ll len2=strlen(s2);
for(int i=,j=;i<len1;i++){
if(s1[i]==s2[j]){
b1[j]=i;
j++;
if(j==len2) break;
}
}
for(int i=len1-,j=len2-;i>=;i--){
if(s1[i]==s2[j]){
b2[j]=i;
j--;
if(j==-) break;
}
}
ll mx=;
mx=max(mx,b1[]);
mx=max(mx,len1-b1[len2-]-); mx=max(mx,b2[]); mx=max(mx,len1-b2[len2-]-); for(int i=;i<len2-;i++){
mx=max(mx,b2[i+]-b1[i]-);
}
cout<<mx;
return ;
}

自己的假题意:我一开始理解的是删除后,第二个串是第一个串的子串,求最大的删除字符数

思路:和上面一样,要求一个前缀和后缀,不过我这个求得前缀和后缀有点区别,

举个栗子:abcdddeffggg  与   bcdfg

那么我就可以组成得的几种组合分别有

bcdfg+""           b+cdfg         bc+dfg        bcd+fg      bcdf+g

分别记录上面的子串第一次出现的位置,和最后出现的一次位置,然后和上面一样求一个max,要记录这些暴力肯定不行,用n次kmp去找位置也不现实,但是其实我们可以只用一次kmp就可以求出来,因为这些子串本身就是前缀的连续关系

可以拿我这个假题意出个题,代码在此奉上

#include<bits/stdc++.h>
#define maxn 200005
#define mod 1000000007
using namespace std;
typedef long long ll;
char s1[maxn],s2[maxn];
ll nxt[maxn],len1,len2;
ll b1[maxn],b2[maxn];
void getnext(){
ll i=,j=-;
nxt[]=-;
while(i<len2){
if(j==-||s1[i]==s2[j]){
nxt[++i]=++j;
}
else j=nxt[j];
}
}
void kmp(char s1[],char s2[],ll b[]){
ll i=,j=;
getnext();
while(i<len1){
if(j==-||s1[i]==s2[j]){
i++;j++;
if(b[j]==-){
b[j]=i;
}
if(j==len2){
j=;
}
}
else j=nxt[j];
}
}
int main(){
cin>>s1>>s2;
len1=strlen(s1);
len2=strlen(s2);
if(len1<=len2){
cout<<"";
return ;
}
for(int i=;i<maxn;i++){
b1[i]=-;
b2[i]=-;
}
kmp(s1,s2,b1);
for(int i=;i<len1/;i++){
char t=s1[i];
s1[i]=s1[len1-i-];
s1[len1-i-]=t;
}
for(int i=;i<len2/;i++){
char t=s2[i];
s2[i]=s2[len2-i-];
s2[len2-i-]=t;
}
kmp(s1,s2,b2);
for(int i=;i<=len2;i++){
if(b1[i]!=-)
b1[i]--;
}
for(int i=;i<=len2/;i++){
ll t=b2[i];
b2[i]=b2[len2-i+];
b2[len2-i+]=t;
}
for(int i=;i<=len2;i++){
if(b2[i]!=-)
b2[i]=len1-b2[i];
}
ll mx=;
if(b1[len2]!=-){
mx=max(b1[len2]-len2+,len1-b1[len2]-);
}
//cout<<mx<<"\n";
if(b2[]!=-){
mx=max(mx,max(b2[],len1-b2[]-len2));
}
//cout<<mx<<"\n";
for(int i=;i<len2;i++){
if(b1[i]!=-&&b2[i+]!=-){
mx=max(mx,b2[i+]-b1[i]-);
}
}
/*for(int i=1;i<=len2;i++){
cout<<b1[i]<<" ";
}
cout<<"\n";
for(int i=1;i<=len2;i++){
cout<<b2[i]<<" ";
}
cout<<"\n";*/
cout<<mx;
return ;
}
/*
abcddbbbzle
cdz
*/

E. Boxers

题目:https://codeforces.com/contest/1203/problem/E

题意:每个数可以变成自己和-1  +1的三种数,除了1,他不能变成比1更小的数,然后给你一组数,问你可以变成几个不同的数

思路:水题,直接从小到大排序,然后能尽量小就尽量小,打打标记即可

#include<bits/stdc++.h>
#define maxn 400005
#define mod 1000000007
using namespace std;
typedef long long ll;
ll a[maxn],n;
ll vis[maxn];
int main(){
cin>>n;
for(int i=;i<=n;i++) cin>>a[i];
sort(a+,a+n+);
ll sum=;
for(int i=;i<=n;i++){ if(vis[a[i]-]==&&a[i]!=){
vis[a[i]-]=;
sum++;
}
else if(vis[a[i]]==){
vis[a[i]]=;
sum++;
}
else if(vis[a[i]+]==){
vis[a[i]+]=;
sum++;
}
}
cout<<sum;
return ;
}

F1. Complete the Projects (easy version)

题目https://codeforces.com/contest/1203/problem/F1

题意:有n个项目,每个项目有个最低要求资格,还有一个价值,会加到自身价值身上,最开始自己有一个价值,然后问是否能做完所有项目,做项目顺序可以自己排

思路:对于价值为正的项目,很明显我们可以直接从小到大的把项目做掉,这样一定是最优的,对于负数来说,我们排差值,差值大的,说明损耗对于自身的损耗较小,这样才能保证自己还有能力做大项目,又能保证做完一个大项目后因为扣的太多而不能去做小项目

#include<bits/stdc++.h>
#define maxn 200005
#define mod 1000000007
using namespace std;
typedef long long ll;
ll n,m;
struct sss
{
ll x,y;
}a[maxn],b[maxn];
ll num1,num2;
int cmp1(struct sss x,struct sss y){
return x.x<y.x;
}
int cmp2(struct sss x,struct sss y){
if(x.x+x.y==y.x+y.y) return x.x>y.x;
return x.x+x.y>y.x+y.y;
}
int main(){
cin>>n>>m;
ll x,y;
for(int i=;i<n;i++){
cin>>x>>y;
if(y>=){
a[num1].x=x;
a[num1++].y=y;
}
else{
b[num2].x=x;
b[num2].y=y;
num2++;
}
}
sort(a,a+num1,cmp1);
sort(b,b+num2,cmp2);
int flag=;
for(int i=;i<num1;i++){
if(m>=a[i].x) m+=a[i].y;
else{
flag=;
break;
}
}
if(flag) printf("NO");
else{
for(int i=;i<num2;i++){
if(m>=b[i].x) m+=b[i].y;
else{
flag=;
break;
}
}
if(!flag&&m>=) printf("YES");
else printf("NO");
}
return ;
}

F2. Complete the Projects (hard version)

题目:https://codeforces.com/contest/1203/problem/F2

题意:和F1一样,但是这个是问能做的最多项目数是多少

思路:对于F1来说直接按差值排,是为了完成所有项目,所以顺序大的小的在前无所谓,但是这个有可能不能完成,但是可以换个方向多完成几个,对于这种情况较多复杂度又要求高的我们就会想到用dp

我们直接对于每个项目来说的话,考虑当前项目取或者不取,但是我们又需要其他价值的最优值,所以其实我们就可以转化成一个01背包,dp[i][j]代表前i件里面j价值能取得最多项目数是多少

#include<bits/stdc++.h>
#define maxn 100005
#define mod 1000000007
using namespace std;
typedef long long ll;
struct sss{
ll x,y;
}a[maxn],b[maxn];
ll n,m,num1=,num2=;
ll dp[][];
int cmp1(struct sss x,struct sss y){
return x.x<y.x;
}
int cmp2(struct sss x,struct sss y){
return x.x+x.y>y.x+y.y;
}
int main(){
scanf("%lld%lld",&n,&m);
for(int i=;i<n;i++){
ll x,y;
scanf("%lld%lld",&x,&y);
if(y>=){
a[num1].x=x;
a[num1++].y=y;
}
else{
b[num2].x=x;
b[num2++].y=y;
}
}
sort(a+,a+num1,cmp1);
sort(b+,b+num2,cmp2);
ll ans=;
for(int i=;i<num1;i++){
if(m>=a[i].x){
ans++;
m+=a[i].y;
}
else break;
}
memset(dp,,sizeof(dp));
for(int i=;i<num2;i++){
for(int j=m;j>=;j--){
if(j+b[i].y>=&&j>=b[i].x) dp[i][j+b[i].y]=max(dp[i-][j+b[i].y],dp[i-][j]+);
else dp[i][j]=max(dp[i][j],dp[i-][j]);
}
}
ll mx=;
for(int i=;i<=m;i++){
mx=max(mx,dp[num2-][i]);
}
cout<<ans+mx;
}

Codeforces Round #579 (Div. 3) 套题 题解的更多相关文章

  1. Codeforces Round #612 (Div. 2) 前四题题解

    这场比赛的出题人挺有意思,全部magic成了青色. 还有题目中的图片特别有趣. 晚上没打,开virtual contest打的,就会前三道,我太菜了. 最后看着题解补了第四道. 比赛传送门 A. An ...

  2. Codeforces Round #741 (Div. 2)部分题题解

    我果然还是太菜了,就写了两道题....真是水死了.... A The Miracle and the Sleeper 简化题意:给定\(l,r\),求\(a\)%\(b\)的最大值,其中\(r> ...

  3. Codeforces Round #361 (Div. 2) 套题

    A - Mike and Cellphone 问有没有多解,每个点按照给出的序列用向量法跑一遍 #include<cstdio> #include<cstring> #incl ...

  4. Codeforces Round #369 (Div. 2) 套题

    A:模拟水题不说 #include <iostream> #include <string.h> #include <algorithm> #include < ...

  5. Codeforces Round #367 (Div. 2) 套题

    吐槽:只能说是上分好场,可惜没打,唉 A:Beru-taxi (水题,取最小值) #include <cstdio> #include <cstring> #include & ...

  6. Codeforces Round #744 (Div. 3) G题题解

    淦,最后一道题没写出来,...还是我太菜了,不过这个题确实比较有趣. G. Minimal Coverage 简化题意:就是你处在坐标轴的0点上,给你一个序列\(a_i\),每次你可以选择向左走\(a ...

  7. Codeforces Round #573 (Div. 2) D题题解

    一.题目 ​ Tokitsukaze, CSL and Stone Game ​ Tokitsukaze和CSL正在玩一些石头游戏. ​ 一开始,有n堆的石头,第i堆石头数记为 \(a_i\),两人轮 ...

  8. Codeforces Round #579 (Div. 3)

    Codeforces Round #579 (Div. 3) 传送门 A. Circle of Students 这题我是直接把正序.逆序的两种放在数组里面直接判断. Code #include &l ...

  9. Codeforces Round #378 (Div. 2) D题(data structure)解题报告

    题目地址 先简单的总结一下这次CF,前两道题非常的水,可是第一题又是因为自己想的不够周到而被Hack了一次(或许也应该感谢这个hack我的人,使我没有最后在赛后测试中WA).做到C题时看到题目情况非常 ...

随机推荐

  1. 手工设计神经MNIST使分类精度达到98%以上

    设计了两个隐藏层,激活函数是tanh,使用Adam优化算法,学习率随着epoch的增大而调低 import tensorflow as tf from tensorflow.examples.tuto ...

  2. 【Qt开发】【Linux开发】Qt程序在嵌入式设备(arm) 上运行,鼠标擦除界面的解决方案

    笔者最近想在arm开发板上,开发一个应用程序,经过网上查询发现qt作为跨平台开发软件很不错,于是便选择了qt开发,笔者的qt版本是4.8.6的.由于arm的主频太低,在arm上进行开发编译,效率会大大 ...

  3. 【Qt开发】【VS开发】VS2010+Qt开发环境搭建

    QT与JAVA有点类似,也是一种跨平台的软件(当然在windows平台和linux平台需要安装相应的QT开发环境和运行库,类似于JAVA在不同平台下的虚拟机JVM环境),因此对于某些需要同时支持win ...

  4. 20191110 Spring Boot官方文档学习(3)

    3.使用Spring Boot 3.1.构建系统 建议选择Maven或Gradle作为构建工具 每个Spring Boot版本都提供了它所支持的依赖关系的精选列表.实际上,您不需要为构建配置中的所有这 ...

  5. python下对文件的操作(非目录)

    总文件夹 子文件夹01 文档01.txt-------------------------------------------------------------------------------- ...

  6. 《剑指offer》面试题23 从上往下打印二叉树 Java版

    注意层序遍历的时候对每一层的处理方式可能不同,这里把每一层的元素保存进一个List中了,那么就需要记录每一层的数量. public List<List<Integer>> se ...

  7. C++中对象的构造顺序

    1,C++ 中的类可以定义多个对象,那么对象构造顺序是怎样的? 1,很多的 bug 是由对象的构造顺序造成的,虽然它不难: 2,对象的构造往往和构造函数牵涉在一起,构造函数的函数体又可能由非常复杂的程 ...

  8. linux的进程间通信概述

    一 进程间通信 1.1. linux内核提供多种进程间通信机制 a. 无名管道和有名管道 b. SystemV IPC:信号量.消息队列.共享内存 c. Socket域套接字 d. 信号 1.2. 无 ...

  9. 2. Docker部署tomcat, nginx, redis,及docker私有仓库

    1. 部署tomcat 1.1 下载tomcat       docker pull tomcat:7-jre8 1.2 部署容器  docker run -di --name=tomcat -p 8 ...

  10. Git 使用疑问

    1)  fatal: remote origin already exists. 解决办法 ..$ git remote add origin git@git.*.com:tang/comment_s ...