牛客周赛 Round 56
A 面包店故事
链接:https://ac.nowcoder.com/acm/contest/88392/A
来源:牛客网
题目描述
小镇上有一家面包店,面包以 𝑥 元的价格出售,加 𝑦 元可以多加几块培根。小歪带着
 𝑛 元来到了面包店,他想知道自己能不能买到加培根的面包?
输入描述:
在一行上输入三个整数 𝑥,𝑦,𝑛(1≤𝑥,𝑦,𝑛≤100) 代表面包的价格、培根的价格和小歪带的钱。
输出描述:
如果小歪能加到培根,在一行上输出 𝑌𝐸𝑆 ;否则,直接输出 𝑁𝑂 。
示例1
输入
 3 1 5
 输出
 YES
说明
面包加培根一共 4 元,小歪带了 5 元,他可以吃到培根!
示例2
输入
 10 1 10
 输出
 NO
说明
面包加培根一共 11 元,小歪带了 10 元,他吃不到培根 (⋟﹏⋞) 。
题解
签到
#include<bits/stdc++.h>
using namespace std;
int x,y,n;
int main(){
    int i,j,k;
    cin>>x>>y>>n;
    if(x+y>n)printf("NO\n");
    else printf("YES\n");
    return 0;
}
B 放课后故事
链接:https://ac.nowcoder.com/acm/contest/88392/B
来源:牛客网
题目描述
小 𝑆 想要举办一个纸飞机大赛,他最新研制出的纸飞机需要 𝑘 张纸才能折成。
 为了制作纸飞机,他向班里的 𝑛 个人要了一些纸,第 𝑖 个人提供了 𝑎𝑖 张纸给小 𝑆 研究纸飞机。 
 放学了,小 𝑆 终于折好了全部的纸飞机,现在有 𝑚 个人留下来和小 𝑆 一起飞纸飞机。 最多有多少个人能分到纸飞机。
输入描述:
第一行输入三个整数 𝑛,𝑚,𝑘(1≤𝑛≤105; 0≤𝑚≤105; 1≤𝑘≤109) 代表班级同学数量、留下来的同学数量和叠一只纸飞机需要的纸的数量。
 第二行输入 𝑛 个整数 𝑎1,𝑎2,…,𝑎𝑛(1≤𝑎𝑖≤109) 代表每一个同学提供的纸的数量。
输出描述:
在一行上输出一个整数,代表最多有多少个人能分到纸飞机。
示例1
输入
 3 2 5
 1 2 4
 输出
 1
说明
小 𝑆 一共收集到 7 张纸,只可以叠一架纸飞机。
示例2
输入
 6 3 4
 1 1 4 5 1 4
 输出
 4
说明
小 𝑆 一共收集到 16 张纸,可以叠 4 架纸飞机,每个人都能分到纸飞机。
题解
草率了,忘记小S自己也算一个,还有long long
#include<bits/stdc++.h>
using namespace std;
#define int long long
int n,m,k,sum,a[100005];
signed main(){
    int i,j;
    cin>>n>>m>>k;
    for(i=1;i<=n;i++){
        cin>>a[i];
        sum+=a[i];
    }
    cout<<min(sum/k,m+1)<<endl;
    return 0;
}
C 异或故事
链接:https://ac.nowcoder.com/acm/contest/88392/C
来源:牛客网
题目描述
给定 𝑡 组询问,76 每次询问都会给出一个正整数 𝑎 ,你需要在区间 [1,109]中找到两个正整数 𝑏 和 𝑐 ,使得 𝑏⊕𝑐=𝑎 。
  ⊕ 代表按位异或。
输入描述:
每个测试文件均包含多组测试数据。第一行输入一个整数 𝑇 (1≤𝑇≤105) 代表数据组数,每组测试数据描述如下:
   在一行上输入一个整数 𝑎 ( 1≤𝑎≤109 )代表76 给出的初始数字。
输出描述:
对于每一组测试数据,在一行上输出两个正整数,代表你找到的两个值。
  如果存在多个解决方案,您可以输出任意一个。
示例1
输入
 3
 1
 5
 4
 输出
 2 3
 3 6
 74 78
说明
对于第一组测试数据,(10)2 xor (11)2 = (01)2 ; 
 对于第二组测试数据,(011)2xor (110)2=(101)2 。
题解
我不知道正解哈,位运算这块我学的不好
 我想到的就是在取出比当前的数大的2的倍数T,然后输出T和T+a,但是好像不对,125分拿75分。
 大佬有知道原因的和我说下吧/(ㄒoㄒ)/~~
#include<bits/stdc++.h>
using namespace std;
#define int long long
int T,a;
signed main(){
    int i,j,k;
    cin>>T;
    while(T--){
        cin>>a;
        int x=1;while(x<=a)x*=2;
        cout<<x<<" "<<x+a<<endl;
    }
    return 0;
}
然后这是正解:
#include<bits/stdc++.h>
using namespace std;
#define int long long
int T,n;
int lowbit(int x){
    return x&(-x);
}
signed main(){
    int i,j,k;
    cin>>T;
    while(T--){
        cin>>n;
        if(n==1)printf("2 3\n");
        else if(n==1000000000)printf("%d %d\n",lowbit(n),(n^lowbit(n)));
        else printf("%d 1\n",n^1);
    }
    return 0;
}
D 构造故事
链接:https://ac.nowcoder.com/acm/contest/88392/D
来源:牛客网
题目描述
小 𝑆 今天在数学课上学习了三角形,他回家立马拿出了自己的 𝑛 根火柴,想知道从这 𝑛 根火柴中任选 3 根,能否组成一个周长最大的三角形。
  由于小 𝑆 只会暴力枚举,所以他把这个问题交给了你,你能帮他解决这个问题吗?
输入描述:
每个测试文件均包含多组测试数据。第一行输入一个整数 𝑇(1≤𝑇≤20) 代表数据组数,每组测试数据描述如下:
  第一行输入一个整数 𝑛(3≤𝑛≤104) 代表小 𝑆 的火柴数量。
  第二行输入 𝑛 个整数 𝑎1,𝑎2,…,𝑎𝑛(1≤𝑎𝑖≤109) 代表每根火柴的长度。
输出描述:
对于每一组测试数据,在一行上输出一个整数,代表能组成周长最大三角形的周长;如果无论如何都无法组成三角形,直接输出 −1 。
示例1
输入
 3
 6
 2 2 10 4 10 6
 5
 6 1 5 3 3
 5
 2 2 4 10 6
 输出
 26
 14
 -1
说明
对于第一组测试数据,有两个合法的三角形 (4,10,10) 和 (6,10,10) 。
题解
排序然后选最大的三个比较能不能构成
#include<bits/stdc++.h>
using namespace std;
#define int long long 
int T,n,a[10005];
signed main(){
    int i,j,k;
    cin>>T;
    while(T--){
        cin>>n;
        for(i=1;i<=n;i++){
            cin>>a[i];
        }
        sort(a+1,a+1+n);
        for(i=n;i>=3;i--){
            if(a[i]<a[i-1]+a[i-2])
                break;
        }
        if(i==2)printf("-1\n");
        else cout<<a[i]+a[i-1]+a[i-2]<<endl;
    }
    return 0;
}
E 约会故事
链接:https://ac.nowcoder.com/acm/contest/88392/E
来源:牛客网
题目描述
情人节才刚刚过去没多久啊 (¯﹃¯∗) ,但是我们的 𝑥𝑞𝑞 已经开始备战明年的情人节了。心灰意冷的他找到小 𝑆 生成了一个虚拟对象小 𝐶 ,在一次次的模拟约会中达成“一起进入电影院”的人生成就。
 𝑥𝑞𝑞 决定向小 𝐶 发送邀请。在设定中,下述情况的小 𝐶 会残忍的拒绝 𝑥𝑞𝑞 的邀请:
  ● 𝑥𝑞𝑞 不在 00:00 后、01:59 前(含)这段小 𝐶 的睡前手机时间里发送邀请;
  ● 𝑥𝑞𝑞 如果在小 𝐶 不开心时发送邀请;
 接受了邀请还远远没有成功!在设定中,下述情况的小 𝐶 会在进入电影院前离去: 
 ● 𝑥𝑞𝑞 到电影院的时间比小 𝐶 晚;
 ● 𝑥𝑞𝑞 给小 𝐶 准备的奶茶不是她喜欢的。
  如果小 𝐶 同意了邀请,且没有中途离去,我们视为 𝑥𝑞𝑞 达成成就!让我们一起来判定——这一次, 𝑥𝑞𝑞 会成功吗。
输入描述:
第一行输入两个整数 𝑛,𝑚(1≤𝑛,𝑚≤105) 代表小 𝐶 感到开心的时间段数量和小 𝐶 喜欢的奶茶数量。
 此后 𝑛 行,第 𝑖 行输入两个长度为 5 ,且形如 ℎℎ:𝑚𝑚 的字符串代表小 𝐶 第 𝑖 段感到开心的起止时间,保证每一段开心时间不超过 24 小时。除了这 𝑛 个时间段外,剩余时间她都是不开心的。 
 第 𝑛+1 行输入 𝑚 个长度不超过 10 且由大小写字母混合构成的字符串 𝑠1,𝑠2,…,𝑠𝑚 代表小 𝐶 喜欢喝的奶茶名字。
 第 𝑛+2 行输入一个整数 𝑞(1≤𝑞≤105) 代表 𝑥𝑞𝑞 尝试次数,每次尝试描述如下:
 ● 第一行输入一个长度为 5,且形如 ℎℎ:𝑚𝑚 的字符串代表 𝑥𝑞𝑞 发送邀请的时间点;
 ● 第二行输入两个长度为 5 ,且形如 ℎℎ:𝑚𝑚 的字符串代表 𝑥𝑞𝑞 到达电影院的时间和小 𝐶 到达电影院的时间,我们约定,他们会在同一天内到达;
 ● 第三行输入一个长度不超过 10 且由大小写字母混合构成的字符串 𝑡 代表 𝑥𝑞𝑞 购买的奶茶名字。
  本题中出现的时间格式均按照 𝐼𝑆𝑂8601 的二十四小时格式标准,即形如 ℎℎ:𝑚𝑚,其中
 ℎℎ(00≤ℎℎ<24) 代表小时数,𝑚𝑚(00≤𝑚𝑚<60) 代表分钟数。
输出描述:
对于每一次尝试,如果 𝑥𝑞𝑞 成功达成成就,在一行上输出 Winner xqq ;如果 𝑥𝑞𝑞 成功邀请但是小 𝐶 中途离开,在一行上输出 Joker xqq ;否则,直接输出 Loser xqq 。
示例1
输入
 3 2
 00:03 00:47
 00:30 01:23
 12:00 17:00
 Lemonade Cappuccino
 5
 00:35
 12:00 12:00
 Cappuccino
 01:23
 13:00 12:59
 Cappuccino
 01:15
 11:00 12:43
 WaTer
 01:24
 09:24 11:00
 Lemonade
 23:59
 08:00 07:43
 LeMonade
 输出
 Winner xqq
 Joker xqq
 Joker xqq
 Loser xqq
 Loser xqq
说明
对于第一次尝试:
 ● 𝑥𝑞𝑞 在 00:35 发送邀请,此时在规定时间内,且小 𝐶 是开心的,所以他的邀请会被接受;● 𝑥𝑞𝑞 在 12:00 到达电影院,此时不晚于小 𝐶 ,且携带了小 𝐶 爱喝的 𝐶𝑎𝑝𝑝𝑢𝑐𝑐𝑖𝑛𝑜 ,所以她不会中途离开。 
 对于第二次尝试,由于迟到了,小 𝐶 中途离开; 
 对于第三次尝试,由于带错了奶茶,小 𝐶 中途离开;
  对于第四次尝试,由于发送邀请时小 𝐶 不开心,所以邀请失败;
  对于第五次尝试,由于发送邀请时不在规定时间内,所以邀请失败。
示例2
输入
 3 1
 00:00 00:00
 22:47 23:59
 23:58 00:17
 AbCdEfGhIj
 1
 00:00
 00:00 00:00
 AbCdEfGhIj
 输出
 Winner xqq
说明
注意,当开心的起始时间和结束时间相等时,我们认为小 𝐶 一整天都感到开心。
题解
模拟,但是!!!
 我有一堆话想说!!!!
 首先,你大半夜的发短信骚扰别人睡觉!
 其次,这个小C这个心情冷热无常!你不行你换一个???
 然后,等不了1分钟的女朋友你要了干啥!!!
 最后,你在现实中你家女朋友这么多次实验??!!!
 纯属的无聊题!!!
 上代码
#include<bits/stdc++.h>
using namespace std;
int n,m,q,hh,mm,t[100005],tag;
string s;
int tim(int hh,int mm){
    return hh*60+mm;
}
unordered_map<string,bool>mp;
int main(){
    int i,j,k;
    scanf("%d%d",&n,&m);
    for(i=1;i<=n;i++){
        scanf("%d:%d",&hh,&mm);
        int tmp=tim(hh,mm);t[tmp]++;
        scanf("%d:%d",&hh,&mm);
        if(tmp>tim(hh,mm))tag++;
        t[tim(hh,mm)+1]--;
    }
    for(i=1;i<100000;i++)t[i]+=t[i-1];
    for(i=0;i<100000;i++)t[i]+=tag;
    for(i=1;i<=m;i++)
    {
        cin>>s;
        mp[s]=true;
    }
    scanf("%d",&q);
    while(q--){
        int flag=2;
        scanf("%d:%d",&hh,&mm);
        if(hh>1||!t[tim(hh,mm)])flag=0;
        scanf("%d:%d",&hh,&mm);
        int tmp=tim(hh,mm);
        scanf("%d:%d",&hh,&mm);
        
        if(tmp>tim(hh,mm)&&flag)flag=1;
        
        cin>>s;if(!mp.count(s)&&flag)flag=1;
        if(flag==2)printf("Winner xqq\n");
        else if(flag==1)printf("Joker xqq\n");
        else printf("Loser xqq\n");
    }
    return 0;
}
F 不是烤串故事
链接:https://ac.nowcoder.com/acm/contest/88392/F
来源:牛客网
题目描述
小红有两个长度为 𝑛 的字符串 𝑠 和 𝑡 ,我们定义下标从 1 开始,现在你可以选取字符串
 𝑠 的前 𝑖 个字符 𝑠1𝑠2⋯𝑠𝑖 ,然后将这一部分反转后与剩余部分拼接,得到 𝑠𝑖′ 。
  请你找到每一个翻转前缀 𝑠𝑖′ 与字符串 𝑡 的  
      
       
        
         
          
          
            max 
           
          
             
           
          
          
          
            i 
           
          
            = 
           
          
            1 
           
          
         
           n 
          
         
        
          _ 
         
        
          len 
         
        
           
         
         
         
           { 
          
         
           lcp 
          
         
            
          
          
          
            ( 
           
           
           
             s 
            
           
             i 
            
           
             ′ 
            
           
          
            , 
           
          
            t 
           
          
            ) 
           
          
         
           } 
          
         
        
       
         \max _{i=1}^{n} \_\operatorname{len}\left\{\operatorname{lcp}\left(s_{i}^{\prime}, t\right)\right\} 
        
       
     i=1maxn_len{lcp(si′,t)},即长度最长的 lcp(𝑠𝑖′,𝑡) 。在这里,lcp 代表最长公共前缀。
  好吧,这其实并不难,作为神秘的 𝐹 题,你同时需要输出满足上述条件的最小的 𝑖 。
 在本题中,反转即为将字符串绕中心字符前后反转,具体地说,设字符串为 𝑠1𝑠2⋯𝑠𝑛−1𝑠𝑛 ,反转后得到 𝑠𝑛𝑠𝑛−1⋯𝑠2𝑠1 。
输入描述:
每个测试文件均包含多组测试数据。第一行输入一个整数 𝑇 (1≤𝑇≤100) 代表数据组数,每组测试数据描述如下:
  第一行输入一个整数 𝑛(1≤𝑛≤106) 代表字符串长度。 
 第二行输入一个长度为 𝑛 ,且仅由小写字母构成的字符串 𝑠。
  第三行输入一个长度为 𝑛 ,且仅由小写字母构成的字符串 𝑡。
  除此之外,保证所有的 𝑛 之和不超过 106 。
输出描述:
对于每一组测试数据,在一行上输出两个整数,代表最长 lcp 长度和在此条件下最小的
 𝑖 。
示例1
输入
 3
 6
 baabaa
 aabbbb
 3
 abc
 bac
 2
 ab
 cd
 输出
 4 3
 3 2
 0 1
说明
对于第一组测试数据,我们这样描述整个过程: 
 ∙ 选择前缀长度为 1 翻转 𝑠1′=“𝑏𝑎𝑎𝑏𝑎𝑎” ,lcp = 0 ;
 ∙ 选择前缀长度为 2 翻转 𝑠2′=“𝑎𝑏𝑎𝑏𝑎𝑎” ,lcp = 1 ; 
 ∙ 选择前缀长度为 3 翻转 𝑠3′=“𝑎𝑎𝑏𝑏𝑎𝑎” ,lcp = 4 ;
 ∙ 选择前缀长度为 4 翻转 𝑠4′=“𝑏𝑎𝑎𝑏𝑎𝑎” ,lcp = 0 ; 
 ∙ 选择前缀长度为 5 翻转 𝑠5′=“𝑎𝑏𝑎𝑎𝑏𝑎” ,lcp = 1 ; 
 ∙ 选择前缀长度为 6 翻转 𝑠6′=“𝑎𝑎𝑏𝑎𝑎𝑏” ,lcp = 3 ;
  所以最长的公共前缀为 4 ,与此同时最小的翻转下标为 3 。
题解

#include<bits/stdc++.h>
using i64 = long long;
using u64 = unsigned long long;
const int P=13331;
const i64 hash_mod = 1610612741;
void solve() {
    int n;
    std::cin >> n;
    std::string s, t;
    std::cin >> s >> t;
    s = ' ' + s, t = ' ' + t;
    std::vector<i64> h1(n + 1), h2(n + 1), h3(n + 1), p(n + 1); 
    p[0] = 1, h1[0] = 0, h3[0] = 0;
    for (int i = 1; i <= n; i++) {
        p[i] = p[i - 1] * P % hash_mod;	
        h1[i] = (h1[i - 1] * P + s[i]) % hash_mod; 
        h3[i] = (h3[i - 1] * P + t[i]) % hash_mod;
    }
    h2[0] = 0;
    std::reverse(s.begin() + 1, s.end());
    for (int i = 1; i <= n; i++) {
        h2[i] = (h2[i - 1] * P + s[i]) % hash_mod; 
    }
    auto get = [&] (int l, int r, std::vector<i64>& h) -> i64 {
        return ((h[r] - h[l - 1] * p[r - l + 1]) % hash_mod + hash_mod) % hash_mod;
    };
    int mx = 0, pos = 1;
    for (int i = 1; i <= n; i++) {
        int l = 1, r = n;
        int ans = -1;
        while(l <= r) {
            int mid = l + r >> 1;
            i64 tar = get(1, mid, h3);
            i64 num = 0;
            if (mid > i) {
                num = get(i + 1, mid, h1);
                num = (num + get(n - i + 1, n, h2) * p[mid - i]) % hash_mod;
            }
            else {
                num = get(n - i + 1, n - i + mid, h2);
            }
            if (tar == num) {
                l = mid + 1;
                ans = mid;
                if (mid > mx) {
                    mx = mid;
                    pos = i;
                }
            }
            else {
                r = mid - 1;
            }
        }
    }
    std::cout << mx << ' ' << pos << '\n'; 
}
signed main() {
    std::ios::sync_with_stdio(0);
    std::cout.tie(0);
    std::cin.tie(0);
    i64 t = 1; 
    std::cin >> t;
    while (t--) {
        solve();
    }
} 
总结




















