牛客 补题

文章分别讲述了两个问题的解决方案。第一个问题是关于25个排列中的矩阵操作,目标是找出一行一列或主副对角线被消除的最长时间,通过记录和比较得出结果。第二个问题涉及图论,计算特定网络中可以构成三角形和直线的数量,通过除以计数因子来修正结果并找到最大公倍数进行简化。
摘要由CSDN通过智能技术生成

F:F:

 思路分析:
在25个排列中总会满足题目给出的条件使得一行一列或主副对角线被消除,我们主要要做的就是记录每一行每一列和主副对角线被完全消除的时间,记录输入顺序并对每个输入的数字进行时间的标记,最后得到一行一列主副对角线上最长的时间,在第一个矩阵的最长时间最短与第二个矩阵的最长时间最短进行比较

#include<iostream>
#include <algorithm>
using namespace std;
int a[10][10];
int b[10][10];
int c;
int t[26];
int minnn(int a,int b,int c,int d)
{
    int k1=min(a,b);
    int k2=min(c,d);
    return min(k1,k2);
}
void solve()
{
    for(int i=1;i<=5;i++)
        for(int j=1;j<=5;j++) cin>>a[i][j];
    for(int i=1;i<=5;i++)
        for(int j=1;j<=5;j++) cin>>b[i][j];
    for(int d=1;d<=25;d++) 
    {
        cin>>c;
        for(int i=1;i<=5;i++)
            for(int j=1;j<=5;j++) 
                if(c==a[i][j]) t[a[i][j]]=d;
        for(int i=1;i<=5;i++)
            for(int j=1;j<=5;j++) 
                if(c==b[i][j])t[b[i][j]]=d;
    }
    int minn1=100;
    for(int i=1;i<=5;i++)
    {
        int minn=0;
        for(int j=1;j<=5;j++)
        {
            minn=max(minn,t[a[i][j]]);
        }
         minn1=min(minn1,minn);
    }
    int minn2=100;
    for(int i=1;i<=5;i++)
    {
        int minn=0;
        for(int j=1;j<=5;j++)
        {
            minn=max(minn,t[a[j][i]]);
        }
        minn2=min(minn2,minn);
	}
    int minn3=100;
    for(int i=1;i<=5;i++)
    {
        int minn=0;
        int is=0;
        for(int j=1;j<=5;j++)
        {
            minn=max (minn,t[b[i][j]]);
        }
        if(!is) minn3=min(minn3,minn);
    }
    int minn4=100;
    for(int i=1;i<=5;i++)
    {
        int minn=0;
        for(int j=1;j<=5;j++)
        {
            
            minn=max (minn,t[b[j][i]]);
        }
        minn4=min(minn4,minn);
	}
    int minn5=100;
    int kk=0;
    for(int i=1;i<=5;i++)
    {
        
        kk=max(kk,t[a[i][i]]);
    }
    minn5=kk;
    int minn6=100;
    kk=0;
	
    for(int i=1;i<=5;i++)
    {
        
        kk=max(kk,t[a[i][5-i+1]]);
    }
    minn6=kk;
        int minn7=100;
    kk=0;
    for(int i=1;i<=5;i++)
    {
       
        kk=max(kk,t[b[i][i]]);
    }
    minn7=kk;
    int minn8=100;
    kk=0;
    for(int i=1;i<=5;i++)
    {
        
        kk=max(kk,t[b[i][5-i+1]]);
    }
    minn8=kk;
    int ans1;
    ans1=minnn(minn1,minn2,minn5,minn6);
    int ans2=minnn(minn3,minn4,minn7,minn8);
	if(ans1<ans2) cout<<1<<endl;
    else if(ans1==ans2) cout<<0<<endl;
    else cout<<2<<endl;
    
}
int main()
{
    int t;
    cin>>t;
    while(t--) solve();
    return 0;
}

J:

 题目中给定三个点,如果三个点之间可以连起来,就可以构成一个三角形,如果既可以联通,又可以不连通,就把他当作一条普通的直线,同时注意,进行遍历时,一个三角形会被数6次,分别是abc,acb,cab,cba,bac,bca;因此所数到的cnt1要÷6;在一条直线上,只要头尾不相同就可以看作是不同的直线,因此数到的直线要÷2才是真正的直线。最后找最大公倍数化简分数。

#include <iostream>
#include <vector>
#include <algorithm>
using namespace std;
vector<int> a[210];
void solve()
{
    int n;
    cin>>n;
    for(int i=1;i<=n;i++) a[i].clear();
    int d;
    cin>>d;
    while(d--)
    {
        int k1,k2;
        cin>>k1>>k2;
        a[k1].push_back(k2);
        a[k2].push_back(k1);
    }
    int cnt1=0,cnt2=0;
    for(int i=1;i<=n;i++)
    {
        for(int j=0;j<a[i].size();j++)
        {
            int dd=a[i][j];
            for(int k=0;k<a[dd].size();k++)
            {
                int kk=a[dd][k];
                if(i==kk) continue;
                cnt2++;
                for(int l=0;l<a[kk].size();l++)
                {
                    int ll=a[kk][l];
                    if(ll==kk) continue;
                    if(ll==i) cnt1++;
                }
            }
        }
    }
    if(cnt1==0)
    {
        cout<<0<<"/"<<1<<endl;
        return;
    }
    int x=__gcd(cnt1/6*3,cnt2/2);
    cout<<cnt1/6*3/x<<"/"<<cnt2/2/x<<endl;
}
int main()
{
    int t;
    cin>>t;
    while(t--) solve();
    return 0;
}

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值