北京化工大学数据结构第十次作业(计算机类)(2022.11.17)

A(附加代码模式)

遍历一遍矩阵算入度出度即可。

#include <bits/stdc++.h>
using namespace std;
#define MAX_SIZE 100
struct Graph
{
    int nodeNumber;
    string vexInfo[MAX_SIZE];
    int adjMatrix[MAX_SIZE][MAX_SIZE];
};
void CalculateDegree(const Graph &g,int inDegree[],int outDegree[])
{
    int n=g.nodeNumber;
    for(int i=0;i<n;i++)
    {
        for(int j=0;j<n;j++)
        {
            if(g.adjMatrix[i][j])
            inDegree[j]++,
            outDegree[i]++;
        }
    }
    return;
}

B

和C是一样的题,只多一步:把出栈顺序储存后输出。

#include <bits/stdc++.h>
using namespace std;
#define MAX_SIZE 100
int main()
{
    int a[100][100];
    int b[100];
    memset(b,0,sizeof(b));
    int n;
    cin>>n;
    for(int i=0;i<n;i++)
    {
        for(int j=0;j<n;j++)
        {
            cin>>a[i][j];
            if(a[i][j]) b[j]++;
        }
    }
    int count=0;
    stack<int> s;
    for(int i=0;i<n;i++)
    {
        if(b[i]==0) s.push(i);
    }
    int c[n];
    while(!s.empty())
    {
        int t=s.top();
        s.pop();
        c[count]=t;
        count++;
        for(int i=0;i<n;i++)
        {
            if(a[t][i]==1) 
            {
                b[i]--;
                if(b[i]==0) s.push(i);
            }
        }
    }
    if(count<n) cout<<"ERROR"<<endl;
    else
    {
        for(int i=0;i<n;i++)
        {
            cout<<c[i];
            if(i!=n-1) cout<<" ";
            else cout<<endl;
        }
    }
    return 0;
}

C

把入度为0的点入栈,然后每次点出栈时就把这个点通向的点入度-1,直到没有点可以入栈为止。判断点数和出栈的点数是否相等。

#include <bits/stdc++.h>
using namespace std;
#define MAX_SIZE 100
int main()
{
    int a[100][100];
    int b[100];
    int n,m;
    while(cin>>n>>m)
    {
        if(n==0 && m==0) break;
        memset(b,0,sizeof(b));
        memset(a,0,sizeof(a));
        for(int i=0;i<m;i++)
        {
            int q1,q2;
            cin>>q1>>q2;
            a[q1-1][q2-1]=1;
            b[q2-1]++;
        }
        int count=0;
        stack<int> s;
        for(int i=0;i<n;i++)
        {
            if(b[i]==0) s.push(i);
        }
        int c[n];
        while(!s.empty())
        {
            int t=s.top();
            s.pop();
            c[count]=t;
            count++;
            for(int i=0;i<n;i++)
            {
                if(a[t][i])
                {
                    b[i]--;
                    if(b[i]==0) s.push(i);
                }
            }
        }
        if(count!=n) cout<<"YES"<<endl;
        else cout<<"NO"<<endl;
    }
    return 0;
}

D

对每个询问,两重循环模拟拓扑排序时的情况,如果序列中的点入度不为0,就输出no。

#include <bits/stdc++.h>
using namespace std;
#define MAX_SIZE 100
int main()
{
    int a[100][100];
    int b[100];
    int n,m;
    cin>>n>>m;
    memset(b,0,sizeof(b));
    memset(a,0,sizeof(a));
    for(int i=0;i<m;i++)
    {
        int q1,q2;
        cin>>q1>>q2;
        a[q1][q2]=1;
        b[q2]++;
    }
    int o;
    cin>>o;
    int c[100],d[100];
    for(int r=0;r<o;r++)
    {
        for(int i=0;i<n;i++)
        {
            c[i]=b[i];
            cin>>d[i];
        }
        for(int i=0;i<n;i++)
        {
            int g=d[i];
            if(c[g]==0)
            {
                for(int j=0;j<n;j++)
                {
                    if(a[g][j]) c[j]--;
                }
            }
            else
            {
                cout<<"NO"<<endl;
                break;
            }
            if(i==n-1) cout<<"YES"<<endl;
        }
    }
    return 0;
}

E

题面描述很有问题,根本看不懂,其实意思就是拓扑排序,每行输入x,y,z表示完成y前必须完成x,耗时为z。求最小时间。

只要在拓扑排序出栈的基础上,用一个数组动态维护最大值就行。

#include <bits/stdc++.h>
using namespace std;
#define MAX_SIZE 100
int main()
{
    int a[100][100];
    int b[100];
    int n,m;
    cin>>n>>m;
    memset(b,0,sizeof(b));
    memset(a,-1,sizeof(a));
    for(int i=0;i<m;i++)
    {
        int q1,q2;
        cin>>q1>>q2;
        cin>>a[q1][q2];
        b[q2]++;
    }
    int count=0;
    stack<int> s;
    int maxm=0,dp[n];
    memset(dp,-1,sizeof(dp));
    for(int i=0;i<n;i++)
    {
        if(b[i]==0) 
        {
            s.push(i);
            dp[i]=0;
            count++;
        }
    }
    while(!s.empty())
    {
        int t=s.top();
        s.pop();
        for(int i=0;i<n;i++)
        {
            if(a[t][i]>=0)
            {   
                if(dp[i]!=-1) dp[i]=max(dp[t]+a[t][i],dp[i]);    
                else dp[i]=dp[t]+a[t][i];
                maxm=max(dp[i],maxm);
                b[i]--;
                if(b[i]==0)
                {
                    count++;
                    s.push(i);
                }
            }
        }
    }
    if(count!=n) cout<<"Impossible"<<endl;
    else cout<<maxm<<endl;
    return 0;
}

F

F-I这4个题都是J题的一部分。

F和E是一样的题。

#include <bits/stdc++.h>
using namespace std;
#define MAX_SIZE 100
int main()
{
    int a[100][100];
    int b[100];
    int n,m;
    cin>>n>>m;
    memset(b,0,sizeof(b));
    memset(a,-1,sizeof(a));
    for(int i=0;i<m;i++)
    {
        int q1,q2;
        cin>>q1>>q2;
        cin>>a[q1][q2];
        b[q2]++;
    }
    int count=0;
    stack<int> s;
    int maxm=0,dp[n];
    memset(dp,-1,sizeof(dp));
    for(int i=0;i<n;i++)
    {
        if(b[i]==0) 
        {
            s.push(i);
            dp[i]=0;
            count++;
        }
    }
    while(!s.empty())
    {
        int t=s.top();
        s.pop();
        for(int i=0;i<n;i++)
        {
            if(a[t][i]>=0)
            {   
                if(dp[i]!=-1) dp[i]=max(dp[t]+a[t][i],dp[i]);    
                else dp[i]=dp[t]+a[t][i];
                maxm=max(dp[i],maxm);
                b[i]--;
                if(b[i]==0)
                {
                    count++;
                    s.push(i);
                }
            }
        }
    }
    for(int i=0;i<n;i++)
    {
        cout<<dp[i];
        cout<<endl;
    }
    return 0;
}

G

G题是建立在F题上的题。

F题把最大值找到后,再把图逆过来(其实就是转置邻接矩阵)后再找一遍最大值,然后用第一遍找到的最大值去减。(或者直接维护最小值,效果一样)

#include <bits/stdc++.h>
using namespace std;
#define MAX_SIZE 100
int main()
{
    int a[100][100];
    int b[100],c[100];
    int n,m;
    cin>>n>>m;
    memset(b,0,sizeof(b));
    memset(a,-1,sizeof(a));
    for(int i=0;i<m;i++)
    {
        int q1,q2;
        cin>>q1>>q2;
        cin>>a[q1][q2];
        b[q2]++;
        c[q1]++;
    }
    int count=0;
    stack<int> s;
    int maxm=0,dp[n];
    memset(dp,-1,sizeof(dp));
    for(int i=0;i<n;i++)
    {
        if(b[i]==0) 
        {
            s.push(i);
            dp[i]=0;
            count++;
        }
    }
    while(!s.empty())
    {
        int t=s.top();
        s.pop();
        for(int i=0;i<n;i++)
        {
            if(a[t][i]>=0)
            {   
                if(dp[i]!=-1) dp[i]=max(dp[t]+a[t][i],dp[i]);    
                else dp[i]=dp[t]+a[t][i];
                maxm=max(dp[i],maxm);
                b[i]--;
                if(b[i]==0)
                {
                    count++;
                    s.push(i);
                }
            }
        }
    }
    int minm,dp2[n];
    memset(dp2,-1,sizeof(dp2));
    for(int i=0;i<n;i++)
    {
        if(c[i]==0) 
        {
            s.push(i);
            dp2[i]=maxm;
            count++;
        }
    }
    while(!s.empty())
    {
        int t=s.top();
        s.pop();
        for(int i=0;i<n;i++)
        {
            if(a[i][t]>=0)
            {   
                if(dp2[i]!=-1) dp2[i]=min(dp2[t]-a[i][t],dp2[i]);    
                else dp2[i]=dp2[t]-a[i][t];
                minm=min(dp2[i],minm);
                c[i]--;
                if(c[i]==0)
                {
                    count++;
                    s.push(i);
                }
            }
        }
    }
    for(int i=0;i<n;i++)
    {
        cout<<dp2[i];
        cout<<endl;
    }
    return 0;
}

H

和F一样的题,注意输出的是什么

#include <bits/stdc++.h>
using namespace std;
#define MAX_SIZE 100
int main()
{
    int a[100][100];
    int b[100],c[100];
    pair<int,int> d[100];
    int n,m;
    cin>>n>>m;
    memset(b,0,sizeof(b));
    memset(a,-1,sizeof(a));
    for(int i=0;i<m;i++)
    {
        int q1,q2;
        cin>>q1>>q2;
        d[i].first=q1;
        d[i].second=q2;
        cin>>a[q1][q2];
        b[q2]++;
        c[q1]++;
    }
    int count=0;
    stack<int> s;
    int maxm=0,dp[n];
    memset(dp,-1,sizeof(dp));
    for(int i=0;i<n;i++)
    {
        if(b[i]==0) 
        {
            s.push(i);
            dp[i]=0;
            count++;
        }
    }
    while(!s.empty())
    {
        int t=s.top();
        s.pop();
        for(int i=0;i<n;i++)
        {
            if(a[t][i]>=0)
            {   
                if(dp[i]!=-1) dp[i]=max(dp[t]+a[t][i],dp[i]);    
                else dp[i]=dp[t]+a[t][i];
                maxm=max(dp[i],maxm);
                b[i]--;
                if(b[i]==0)
                {
                    count++;
                    s.push(i);
                }
            }
        }
    }
    int minm,dp2[n];
    memset(dp2,-1,sizeof(dp2));
    for(int i=0;i<n;i++)
    {
        if(c[i]==0) 
        {
            s.push(i);
            dp2[i]=maxm;
            count++;
        }
    }
    while(!s.empty())
    {
        int t=s.top();
        s.pop();
        for(int i=0;i<n;i++)
        {
            if(a[i][t]>=0)
            {   
                if(dp2[i]!=-1) dp2[i]=min(dp2[t]-a[i][t],dp2[i]);    
                else dp2[i]=dp2[t]-a[i][t];
                minm=min(dp2[i],minm);
                c[i]--;
                if(c[i]==0)
                {
                    count++;
                    s.push(i);
                }
            }
        }
    }
    for(int i=0;i<m;i++)
    {
        cout<<dp[d[i].first]<<endl;
        //cout<<dp2[i];
        //cout<<endl;
    }
    return 0;
}

I

和G一样的题,注意输出的是什么。

#include <bits/stdc++.h>
using namespace std;
#define MAX_SIZE 100
int main()
{
    int a[100][100];
    int b[100],c[100];
    pair<int,int> d[100];
    int n,m;
    cin>>n>>m;
    memset(b,0,sizeof(b));
    memset(a,-1,sizeof(a));
    for(int i=0;i<m;i++)
    {
        int q1,q2;
        cin>>q1>>q2;
        d[i].first=q1;
        d[i].second=q2;
        cin>>a[q1][q2];
        b[q2]++;
        c[q1]++;
    }
    int count=0;
    stack<int> s;
    int maxm=0,dp[n];
    memset(dp,-1,sizeof(dp));
    for(int i=0;i<n;i++)
    {
        if(b[i]==0) 
        {
            s.push(i);
            dp[i]=0;
            count++;
        }
    }
    while(!s.empty())
    {
        int t=s.top();
        s.pop();
        for(int i=0;i<n;i++)
        {
            if(a[t][i]>=0)
            {   
                if(dp[i]!=-1) dp[i]=max(dp[t]+a[t][i],dp[i]);    
                else dp[i]=dp[t]+a[t][i];
                maxm=max(dp[i],maxm);
                b[i]--;
                if(b[i]==0)
                {
                    count++;
                    s.push(i);
                }
            }
        }
    }
    int minm,dp2[n];
    memset(dp2,-1,sizeof(dp2));
    for(int i=0;i<n;i++)
    {
        if(c[i]==0) 
        {
            s.push(i);
            dp2[i]=maxm;
            count++;
        }
    }
    while(!s.empty())
    {
        int t=s.top();
        s.pop();
        for(int i=0;i<n;i++)
        {
            if(a[i][t]>=0)
            {   
                if(dp2[i]!=-1) dp2[i]=min(dp2[t]-a[i][t],dp2[i]);    
                else dp2[i]=dp2[t]-a[i][t];
                minm=min(dp2[i],minm);
                c[i]--;
                if(c[i]==0)
                {
                    count++;
                    s.push(i);
                }
            }
        }
    }
    for(int i=0;i<m;i++)
    {
        //cout<<dp[d[i].first]<<endl;
        cout<<dp2[d[i].second]-a[d[i].first][d[i].second];
        //cout<<dp2[i];
        cout<<endl;
    }
    return 0;
}

J

把F-I四个题拼在一起就行。 

#include <bits/stdc++.h>
using namespace std;
#define MAX_SIZE 100
int main()
{
    int a[100][100];
    int b[100],c[100];
    pair<int,int> d[100];
    int n,m;
    cin>>n>>m;
    memset(b,0,sizeof(b));
    memset(a,-1,sizeof(a));
    for(int i=0;i<m;i++)
    {
        int q1,q2;
        cin>>q1>>q2;
        d[i].first=q1;
        d[i].second=q2;
        cin>>a[q1][q2];
        b[q2]++;
        c[q1]++;
    }
    int count=0;
    stack<int> s;
    int maxm=0,dp[n];
    memset(dp,-1,sizeof(dp));
    for(int i=0;i<n;i++)
    {
        if(b[i]==0) 
        {
            s.push(i);
            dp[i]=0;
            count++;
        }
    }
    while(!s.empty())
    {
        int t=s.top();
        s.pop();
        for(int i=0;i<n;i++)
        {
            if(a[t][i]>=0)
            {   
                if(dp[i]!=-1) dp[i]=max(dp[t]+a[t][i],dp[i]);    
                else dp[i]=dp[t]+a[t][i];
                maxm=max(dp[i],maxm);
                b[i]--;
                if(b[i]==0)
                {
                    count++;
                    s.push(i);
                }
            }
        }
    }
    int minm,dp2[n];
    memset(dp2,-1,sizeof(dp2));
    for(int i=0;i<n;i++)
    {
        if(c[i]==0) 
        {
            s.push(i);
            dp2[i]=maxm;
            count++;
        }
    }
    while(!s.empty())
    {
        int t=s.top();
        s.pop();
        for(int i=0;i<n;i++)
        {
            if(a[i][t]>=0)
            {   
                if(dp2[i]!=-1) dp2[i]=min(dp2[t]-a[i][t],dp2[i]);    
                else dp2[i]=dp2[t]-a[i][t];
                minm=min(dp2[i],minm);
                c[i]--;
                if(c[i]==0)
                {
                    count++;
                    s.push(i);
                }
            }
        }
    }
    for(int i=0;i<m;i++)
    {
        int g1=dp[d[i].first];
        int g2=dp2[d[i].second]-a[d[i].first][d[i].second];
        if(g1==g2)
        {
            cout<<d[i].first<<"-->"<<d[i].second<<":"<<g1<<endl;
        }
    }
    return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

五百场cf灰名

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值