链接:https://ac.nowcoder.com/acm/contest/5026/A
来源:牛客网
题目描述
你是一个勇士,现在你准备去森林刷毛球怪,你有两个属性(血量,攻击力),毛球怪也有这两个属性。当你遭遇一只毛球怪时你们会进入战斗,然后你和毛球怪轮流攻击(你先手),每次使对方的血量减去自己攻击力的数值,当一方的血量小于等于 0 时死亡。现在你想知道在自己活着的前提下最多杀死几只毛球怪
#include<iostream> using namespace std; int main() { int t,h,a,H,A; cin>>t; while(t--) { cin>>h>>a>>H>>A; if(A==0||H==0) cout<<-1<<endl; else if(a==0||h==0) cout<<0<<endl; else{ int l=0,m=0; if(H%a==0) l=H/a; else l=H/a+1; if(l>1) { m=h/((l-1)*A); if(h%((l-1)*A)==0) m--; cout<<m<<endl; } else cout<<-1<<endl; } } }
链接:https://ac.nowcoder.com/acm/contest/5026/B
来源:牛客网
题目描述
现在米咔想知道,最少用多少天他可以吃光苹果和香蕉。
可以证明的是,一定存在一种方案可以让米咔在若干天后吃光苹果和香蕉。
emm。。题解很清楚。我刚开始想的是,n!=m的时候,最后都会吃到 某种水果剩余1 另一种为x的情况。但显然不是很好的策略。为了让天数最少,那么最可能的就是
是两者最为接近;就是题解上写的,让x=min(m,n)不断乘2与y=max(n,m)接近。导致x>y/2&&x<=y;此时,令t=y-x,则(x大于t,因为x>y/2,所以x一定大于t)x减小到t,此时y=2*t。差不多是倍增思想
#include<iostream> #include<algorithm> using namespace std; bool check(int x) { int ans=0; while(x) { x>>=1; if(x%2) return 0; ans++; } return ans; } int main() { int t,n,m; cin>>t; while(t--) { cin>>n>>m; if(n<m) swap(n,m); int k=0; if(n==m) {cout<<n<<endl;continue;} while(2*m<n) m=m*2,k++; int t=n-m; k+=m+t+1; cout<<k<<endl; }
链接:https://ac.nowcoder.com/acm/contest/5026/C
来源:牛客网
题目描述
众所周知,高考数学中有一个题目是给出12个单项选择,每一个选择的答案是 A,B,C,D 中的一个。
网上盛传答案存在某种规律,使得蒙对的可能性大大增加。于是今年老师想让你安排这12个题的答案。但是他有一些条件,首先四个选项的数量必须分别为 na,nb,nc,nd。其次有 m 个额外条件,分别给出两个数字 x,y,代表第 x 个题和第 y 个题的答案相同。 现在你的老师想知道,有多少种可行的方案安排答案。来源:牛客网
题目描述
给定一个有向带权图,其中包括 n个城市,城市编号从1 到n,有向边的编号从 1 到 m,现在有一个人位于城市 1,并且想要到城市n旅游。现在政府正在决定将一条道路反向,这个人想知道在某一指定道路反向的情况到达城市n最短路径长度会不会变短。
保证开始给定的图从城市1可以到达城市n,若边反向后城市1不能到达城市n,我们视为最短路径长度没有变短。
正向跑一遍记录在dis【】;
反向跑一遍记录在dis1【】;
假设反向u->v的边,则为1->v->u->n,即值变为dis【v】+dis1【u】+w(u,v),将值与dis[u]进行比较;
代码重复部分有点多~~
#include<iostream> #include<algorithm> #include<queue> #include<cstring> using namespace std; #define maxn 500000 long long n,cnt,head[maxn],cnt1,head1[maxn],m,dis[maxn],dis1[maxn]; struct node{ long long u,dis; bool operator<(const node&rhs)const{ return dis>rhs.dis;} }; struct edge{ long long nx,to; long long w; long long num; }edge[maxn]; struct edge1{ long long nx,to; long long w; long long num; }edge1[maxn]; struct e{ long long u,v,w; }e[maxn]; void add(long long u,long long v,long long w,long long i) { edge[++cnt].nx=head[u]; edge[cnt].to=v; edge[cnt].w=w; edge[cnt].num=i; head[u]=cnt; } void add1(long long u,long long v,long long w,long long i) { edge1[++cnt1].nx=head1[u]; edge1[cnt1].to=v; edge1[cnt1].w=w; edge1[cnt1].num=i; head1[u]=cnt1; } void bfs(long long s) { priority_queue<node> Q; Q.push((node){s,0}); dis[s]=0; while(!Q.empty()) { node f=Q.top(); Q.pop(); long long u=f.u,d=f.dis; if(d>dis[u]) continue; for(long long i=head[u];i;i=edge[i].nx) { long long v=edge[i].to,w=edge[i].w; if(dis[v]>dis[u]+w){ dis[v]=dis[u]+w; Q.push((node){v,dis[v]}); } } } } void bfs1(long long s) { priority_queue<node> Q; Q.push((node){s,0}); dis1[s]=0; while(!Q.empty()) { node f=Q.top(); Q.pop(); long long u=f.u,d=f.dis; if(d>dis1[u]) continue; for(long long i=head1[u];i;i=edge1[i].nx) { long long v=edge1[i].to,w=edge1[i].w; if(dis1[v]>dis1[u]+w){ dis1[v]=dis1[u]+w; Q.push((node){v,dis1[v]}); } } } } int main() { cin>>n>>m; memset(dis,0x3f,sizeof(dis)); memset(dis1,0x3f,sizeof(dis1)); for(long long i=1;i<=m;i++) { long long u,v,c; cin>>u>>v>>c; e[i].u=u,e[i].v=v,e[i].w=c; add(u,v,c,i);add1(v,u,c,i); } bfs(1); bfs1(n); int q=0; cin>>q; while(q--) { long long x; cin>>x; long long val=(long long)(dis[e[x].v]+dis1[e[x].u]+e[x].w); if(val<(long long)dis[n]) cout<<"YES"<<endl; else cout<<"NO"<<endl; } }
链接:https://ac.nowcoder.com/acm/contest/5026/E
来源:牛客网
题目描述
#include<iostream> #include<algorithm> #include <unordered_map> #include<cstring> #include <bits/stdc++.h> using namespace std; #define p 127 #define ll long long #define maxn 300000 unsigned long long Hash[500000],pow1[maxn]; ll dp[500000]; char s[maxn]; ll n,k; #define re register #define il inline il long long read() { re ll x=0,f=1;char c=getchar(); while(c<'0'||c>'9'){ if(c=='-') f=-1;c=getchar(); } while(c>='0'&&c<='9') x=(x<<3)+(x<<1)+(c^48),c=getchar(); return x*f; } unsigned long long hash1(ll i,ll mid)//hash初始化 { return Hash[i+mid-1]-Hash[i-1]*pow1[mid]; } bool check(ll mid) { long long num=0; dp[0]=0; unordered_map<unsigned long long,ll> MAP; for(ll i=n-mid+1;i>0;i--)//倒序枚举,也可以用正序,hash就需要倒序了~~ { MAP[hash1(i+mid,mid)]=dp[i+mid];//可以手动模拟一下。MAP<hash,dp>,对于从i开始串长为mid的哈希值,赋值给dp【i+mid】, dp[i]=MAP[hash1(i,mid)]+1;//当前dp【i】为hash中与该子串值相同+1,感觉解释的有点错误~~手动模拟吧,应该就会了 num=max(num,dp[i]); } if(num<k) return false; else return true; } int main() { n=read(),k=read(); cin>>s+1; for(ll i=1;i<=n;i++) Hash[i]=Hash[i-1]*p+s[i]-'a'; ll l=0,r=n/k+1,ans=0; pow1[0]=1; for(ll i=1;i<=n;i++) pow1[i]=pow1[i-1]*p;//初始化pow1数组 while(l<=r) { ll mid=(l+r+1)>>1;//扩大一点搜索范围,保险~~ if(check(mid)) ans=max(ans,mid), l=mid+1; else r=mid-1; } cout<<ans; return 0; }
来源:牛客网
题目描述
给定一个由n个点和n-1条边组成的无向连通图(即一棵树),每一条边都有一个权值代表走过它所需要的时间花费,每个点上面有初始有一个苹果,每个苹果有一个成熟度。
由于苹果不熟或者熟的太透了都不会好吃,所以现在米咔想摘一个成熟度在范围[x,y]的苹果来做苹果派。现在需要你来执行m条操作。
1 u x:在某一个点u新出现了一个成熟度为x的苹果。(1≤u≤n,1≤x≤10000)
2 u x y:询问米咔从某一个点u出发,去摘一个成熟度在[x,y]范围内的苹果并回到u的最小时间花费。(1≤u≤n,1≤x≤y≤10000)