A:开场白
分析:模拟,length%m!=0,输出No,反之,四个为一组遍历一遍
#include <iostream>
#include <cmath>
#include <algorithm>
#include <vector>
#include <set>
//#include <unordered_map>
#include <map>
#include <queue>
#include <cstdio>
#include <cstdlib>
#include <string>
#include <utility>
#include <cstring>
//#include <multimap>
#define ll long long
#define inf 0x3f3f3f3
using namespace std;
const int mxn = 2e5+10;
#define TLE std::ios::sync_with_stdio(false);cin.tie(NULL);cout.tie(NULL);
#define ls now<<1,l,mid
#define rs now<<1|1,mid+1,r
#define lc now<<1
#define rc now<<1|1
#define upsum(now) rt[now].sum =rt[now<<1].sum + rt[now<<1|1].sum ;
#define upmx(now) rt[now].mx = max(rt[now<<1].mx , rt[now<<1|1].mx) ;
#define pb push_back
ll n,m,k,t,mx,mn,l,r,dp[mxn],u,v,cost,ans[mxn],a[mxn];
string str;
int main()
{
TLE;
cin>>t;
while(t--)
{
cin>>str;
if(str.size()%4 || str.size()<4)
cout<<"No"<<endl;
else
{
int flag =0 ;
for(int i=0;i<str.size();)
{
if(str[i]=='2' && str[i+1]=='0' && str[i+2]=='5' && str[i+3]=='0')
i+=4;
else
{
flag = 1 ; break;
}
}
if(flag) cout<<"No"<<endl;
else
cout<<"Yes"<<endl;
}
}
}
B:时间间隔
分析:年,月,日,时,别60%100==0,所以只需要考虑分和秒
3600-60 * score-seconds ,或者按seconds 是否为0分类讨论一下,和前面做法类似
#include <iostream>
#include <cmath>
#include <algorithm>
#include <vector>
#include <set>
//#include <unordered_map>
#include <map>
#include <queue>
#include <cstdio>
#include <cstdlib>
#include <string>
#include <utility>
#include <cstring>
//#include <multimap>
#define ll long long
#define inf 0x3f3f3f3
using namespace std;
const int mxn = 2e5+10;
#define TLE std::ios::sync_with_stdio(false);cin.tie(NULL);cout.tie(NULL);
#define ls now<<1,l,mid
#define rs now<<1|1,mid+1,r
#define lc now<<1
#define rc now<<1|1
#define upsum(now) rt[now].sum =rt[now<<1].sum + rt[now<<1|1].sum ;
#define upmx(now) rt[now].mx = max(rt[now<<1].mx , rt[now<<1|1].mx) ;
#define pb push_back
int n,m,k,t,mx,mn,l,r,dp[mxn],u,v,cost,ans[mxn],a[mxn];
string str;
int main()
{
scanf("%d",&t);
while(t--)
{
scanf("%d-%d-%d %d:%d:%d",&n,&m,&k,&l,&r,&v);
printf("%d\n",( 3600-r*60-v) % 100 );
}
}
C:分宿舍(决策性问题)
首先在不考虑情侣间的情况下,预处理一下max(m+k,n+k)范围内费用最优化(降低时间复杂度),每次处理 i 的时候,我们可以将i与i-1或者i-2或者i-3分到一个新房间,需要注意的是如果n<=3,会出现错误,所以我们需要提前将三个人住宿费用单独处理一下,达到费用最小,预处理完以后,枚举情侣间k,在预处理的ans表中查找剩余人数的最优开房费用。
或者是开一个二维dp数组,一维存放情侣间的数量,然后枚举双人间,每次二维数组存最小值费用(这里两人间和三人间是一个一次函数,似乎可以优化),然后遍历dp数组找到最小值。O( k*max(n+k,m+k) ) ?
再或者枚举情侣间,分5种情况讨论。
#include <iostream>
#include <cmath>
#include <algorithm>
#include <vector>
#include <set>
//#include <unordered_map>
#include <map>
#include <queue>
#include <cstdio>
#include <cstdlib>
#include <string>
#include <utility>
#include <cstring>
//#include <multimap>
#define ll long long
#define inf 0x3f3f3f3
const long long INF = 0x3f3f3f3f3f3f3f3f ;
using namespace std;
const int mxn = 2e3+10;
#define TLE std::ios::sync_with_stdio(false);cin.tie(NULL);cout.tie(NULL);
#define ls now<<1,l,mid
#define rs now<<1|1,mid+1,r
#define lc now<<1
#define rc now<<1|1
#define upsum(now) rt[now].sum =rt[now<<1].sum + rt[now<<1|1].sum ;
#define upmx(now) rt[now].mx = max(rt[now<<1].mx , rt[now<<1|1].mx) ;
#define pb push_back
ll n,m,k,t,mx,mn,l,r,dp[mxn][mxn],u,v,cost,ans[mxn],a[mxn];
string str;
int main()
{
TLE;
cin>>t;
while(t--)
{
cin>>n>>m>>k>>l>>r>>v;
ans[1] = ans[2] = min(l,r) ; ans[3] = min( 2*l,r );
ll cnt = INF;
for(int i=4; i<=max( n+k,m+k ); i++)
ans[i] = min( ans[i-1]+min(l,r), min( min ( ans[i-2]+l,ans[i-2]+r ),ans[i-3]+r ) );
for(int i=0; i<=k; i++)
cnt = min(cnt,i*v+ans[n+k-i]+ans[m+k-i]);
cout<<cnt<<endl;
}
return 0 ;
}
D:PASS
map容器储存遍历
#include <iostream>
#include <cmath>
#include <algorithm>
#include <vector>
#include <set>
//#include <unordered_map>
#include <map>
#include <queue>
#include <cstdio>
#include <cstdlib>
#include <string>
#include <utility>
#include <cstring>
//#include <multimap>
#define ll long long
#define inf 0x3f3f3f3
using namespace std;
const int mxn = 2e5+10;
#define TLE std::ios::sync_with_stdio(false);cin.tie(NULL);cout.tie(NULL);
#define ls now<<1,l,mid
#define rs now<<1|1,mid+1,r
#define lc now<<1
#define rc now<<1|1
#define upsum(now) rt[now].sum =rt[now<<1].sum + rt[now<<1|1].sum ;
#define upmx(now) rt[now].mx = max(rt[now<<1].mx , rt[now<<1|1].mx) ;
#define pb push_back
int n,m,k,t,mx,mn,l,r,dp[mxn],u,v,cost,ans[mxn],a[mxn];
string str;
int main()
{
TLE;
cin>>t;
while(t--)
{
cin>>n>>m>>k;
map<int,int>m1,m2;
int mid = n/2,cnt=0;
for(int i=1;i<=n;i++)
{
cin>>l;
if(i<=mid) m1[l]++;
m2[l]++;
}
for(int i=1;i<=m;i++)
cnt+=min( m2[i]/k,m1[i] );
cout<<cnt<<endl;
}
}
F:冰水挑战
dp【i】【j】表示i个挑战中选择j个后的最大体力值,那么每次只考虑第i个挑战能否作为第j个挑战来考虑,将挑战与否的最大体力值存到dp【i】【j】
#include <iostream>
#include <cmath>
#include <algorithm>
#include <vector>
#include <set>
//#include <unordered_map>
#include <map>
#include <queue>
#include <cstdio>
#include <cstdlib>
#include <string>
#include <utility>
#include <cstring>
//#include <multimap>
#define ll long long
#define inf 0x3f3f3f3f
const long long INF = 0x3f3f3f3f3f3f3f3f ;
using namespace std;
const int mxn = 1e3+10;
#define TLE std::ios::sync_with_stdio(false);cin.tie(NULL);cout.tie(NULL);
#define ls now<<1,l,mid
#define rs now<<1|1,mid+1,r
#define lc now<<1
#define rc now<<1|1
#define upsum(now) rt[now].sum =rt[now<<1].sum + rt[now<<1|1].sum ;
#define upmx(now) rt[now].mx = max(rt[now<<1].mx , rt[now<<1|1].mx) ;
#define pb push_back
ll n,m,k,t,mx,mn,l,r,dp[mxn][mxn],u,v,cost,ans[mxn],a[mxn];
string str;
struct node
{
ll a,b,c;
} no[mxn];
int main()
{
TLE;
cin>>t;
while(t--)
{
cin>>n>>m;
for(int i=1; i<=n; i++)
cin>>no[i].a>>no[i].b>>no[i].c;
memset(dp,-1*inf,sizeof(dp));
dp[0][0] = m ;
for(int i=1; i<=n; i++)
{
dp[i][0] = dp[i-1][0] + no[i].c ; /// 不参加任何挑战
for(int j=1; j<=i; j++)
{
dp[i][j] = dp[i-1][j] + no[i].c ; /// j个挑战中,不包含第i个挑战的体力
ll tmp = min(dp[i-1][j-1],no[i].b)-no[i].a ; /// 第i个挑战作为第j个挑战的体力值
if(tmp>0)
dp[i][j] = max(dp[i][j],tmp+no[i].c);
}
}
for(ll i=n; i>=0; i--)
{
if(dp[n][i]>0)
{
cout<<i<<endl;
break;
}
}
}
return 0 ;
}
H-骑行
一:每段初速度为0,按能否达到最大速度讨论,能的话time += 加速时间+匀速时间 ;
反之,time += ( sqrt( 2ax+v0^2 ) - v0 )/a ;
二,要在最短时间内通过N段路,那么,使每段路的末端速度小于等于下一段的限速度就可以最快,那么,如果直接处理的话,会存在这样一个问题:前面K段路程都可以加速,但在第K+1段路程前速度不能变为第K+1段路程的限速度,那么,想要避免这个问题,可以逆序处理所有的限速度,第N段单独处理,第N-1段的速度更新为min ( no[i].v , sqrt( no[i+1].v^2+2*no[i].a * no[i].x ) ) ,因为使逆序处理,那么这里更新的就是该段路逆序时的末速度,正序时的最大速度。令初速度v=0,如果当前路段速度小于下一路段的速度,那么,处于加速路段,如果达到最大速度时,没有跑完该段路程,那么 time += 加速时间+匀速时间 ;反之,time += 加速时间;如果当前路段速度大于下一路段的速度,那么如果当前速度v减速到进入下一路段允许达到的最大速度所走的路程刚好时该路程的长度,那么time += 减速时间 ,反之,就要分加速段,匀速段以及减速段去计算时间,time += 加速段时间 + 匀速段+减速段时间。
PS:下面的代码来源于理解错题意的聚聚,但能A掉,很玄学!
#include <iostream>
#include <cmath>
#include <algorithm>
#include <vector>
#include <set>
//#include <unordered_map>
#include <map>
#include <queue>
#include <cstdio>
#include <cstdlib>
#include <string>
#include <utility>
#include <cstring>
//#include <multimap>
#define ll long long
#define inf 0x3f3f3f3f
const long long INF = 0x3f3f3f3f3f3f3f3f ;
using namespace std;
const int mxn = 1e3+10;
#define TLE std::ios::sync_with_stdio(false);cin.tie(NULL);cout.tie(NULL);
#define ls now<<1,l,mid
#define rs now<<1|1,mid+1,r
#define lc now<<1
#define rc now<<1|1
#define upsum(now) rt[now].sum =rt[now<<1].sum + rt[now<<1|1].sum ;
#define upmx(now) rt[now].mx = max(rt[now<<1].mx , rt[now<<1|1].mx) ;
#define pb push_back
int n,m,k,t,mx,mn,l,r,dp[mxn][mxn],u,v,cost,ans[mxn],a[mxn];
string str;
struct node
{
double x,v,a;
}no[mxn];
int main()
{
TLE;
scanf("%d",&t);
while(t--)
{
scanf("%d",&n);
double tim = 0 , v = 0 ;
for(int i=1;i<=n;i++)
{
scanf("%lf %lf %lf",&no[i].x,&no[i].v,&no[i].a);
tim += (sqrt(no[i].x*no[i].a*2.0) <= no[i].v ? sqrt(2.0*no[i].x/no[i].a) : sqrt( no[i].v*no[i].v )+(no[i].x-no[i].v*no[i].v/2.0*no[i].a)/no[i].v );
}
printf("%.10lf\n",tim) ;
}
return 0 ;
}