牛客算法周周练6

闲聊:这次的有点简单.....
A题:看了一下感觉像汉诺塔问题....
假设最开始n=0,也就是石墩数为0,此时荷叶数为m,那么可以过去图片说明 只青蛙,相信这个大家都知道
现在n=1,我们可以由前一个状态得到,可以假设1号石墩为上一个的终点的石墩,那么除了1号石墩,剩下的状态为n=0的状态,此时可以跳过来m+1个,然后现在1号石墩上还剩余m+1个,把这m+1个每个荷叶和1号石墩上各一个,然后逐步累加到终点石墩上,此时答案为图片说明
现在n=2,那么我们同理2号石墩等于n=1时终点石墩的状态,然后剩下的状态就为拿n=1时候的状态,那么为图片说明
然后多写几个发现图片说明

#include<bits/stdc++.h>
using namespace std;
int main()
{
  int n,m;
  cin>>n>>m;
cout<<(m+1)*(1<<n);
}

B题:蒙一发图片说明 然后过了.......
多写几组看看就行,具体解释就跳了

#include<bits/stdc++.h>
using namespace std;
int main()
{
   long long a,b,c;
    cin>>a>>b>>c;
    cout<<__gcd(a,b);
}

C题:咦!分解到不能分解然后算输
唯一分解定理:任何一个大于1的自然数 N,如果N不为质数,那么N可以唯一分解成有限个质数的乘积
也就是图片说明
P为质数,a为幂次
然后就是判断幂次和的奇偶

#include <bits/stdc++.h>
using namespace std;

int main()
{
    int n;
    scanf("%d",&n);
    if(n==1) printf("Nancy\n");
    else
    {
        int num=0;
        for(int i=2;i<=n;i++)
        {
            while(n%i==0)
            {
                n/=i;
                num++;
            }
        }
        printf(num&1?"Nancy\n":"Johnson\n");
    }

    return 0;
}

D题:读完感觉最小生成树的裸体,可能是错觉,咦!好像真的是裸题
keruskal直接套.....
并查集+边权贪心

#include<bits/stdc++.h>
using namespace std;
int n,m;
struct edges
{
    int s,t,w;
    bool operator<(const edges &e) const{
        return w<e.w;
    }
}edge[500005];
inline int read(void)
{
    int s=0,f=1;
    char c=getchar();
    while(c>'9'||c<'0'){if(c=='-')f=-1;c=getchar();}
    while(c>='0'&&c<='9') {s=s*10+c-'0';c=getchar();}
    return f*s;
}
int parent[100005];
int find(int x){
    return parent[x]==x?parent[x]:parent[x]=find(parent[x]);
}
long long keruskal(void)
{
    long long sum=0,cnt=0;
    for(int i=1;i<=m;i++){
        if(cnt==n-1) break;
        int u=edge[i].s;int v=edge[i].t;
        if(find(u)!=find(v)){
            sum+=edge[i].w;
            parent[find(u)]=find(v);
            cnt++;
        }
    }
    return sum;
}
int main(void)
{
    n=read();m=read();
    for(int i=1;i<=n;i++)parent[i]=i;
    for(int i=1;i<=m;i++){
        edge[i].s=read();edge[i].t=read();edge[i].w=read();
    }
    sort(edge+1,edge+m+1);
    cout<<keruskal();
}

E题:有毒的签到题
代码补全???,反正队友写的暴力过了.........
具体看代码......

int main()
{
    scanf("%d%d", &N, &maxL);
    while (N--)
    {
        int opt, x, y;
        scanf("%d%d%d", &opt, &x, &y);
        if (opt == 1)
        {
            if (L.find(make_pair(x, y)) != L.end())
                continue;
            L.insert(make_pair(x, y));
            for (int i = x; i <= y; ++i)
            {
                a[i]++;
                if (a[i] == 1)
                    ans++;
            }
        }
        if (opt == 2)
        {
            if (L.find(make_pair(x, y)) == L.end())
                continue;
            L.erase(make_pair(x, y));
            for (int i = x; i <= y; ++i)
            {
                a[i]--;
                if (a[i] == 0)
                    ans--;
            }
        }
        if (opt == 3)
            printf("%d\n", ans);
    }
    return 0;
}
全部评论

相关推荐

点赞 收藏 评论
分享
牛客网
牛客企业服务