1. 程式人生 > 其它 >圖著色問題

圖著色問題

題目詳情 - 7-1 圖著色問題 (25 分) (pintia.cn)

給一個(V,E)的無向圖,k種顏色,給每個點都染色,看看染的色能不能讓相鄰的兩個點不是同一種顏色,可以輸出yes,不可以輸出no

其實在做題目要快準狠,看一段長文字,就知道考的哪個點,提煉出要點才是主要的,而不是其他的一些花裡胡哨的東西

本題:①必須要用滿k種顏色②不是樹,只是圖,也就是圖不一定連通,可以用dfs其實

但這個題資料範圍挺小,可以直接暴力

dfs:

#include<iostream>
#include<cstring>
using namespace std;
int n,m,k;
const int N=1000; int mp[N][N],st[N],s[N],a[N],f; void dfs(int u) { for(int i=1;i<=n;i++) { if(mp[u][i]) { if(a[u]==a[i]) { f=0; return ; } if(!st[i]) { st[i]=1; dfs(i); } } } }
int main(){ cin>>n>>m>>k; while(m--) { int a,b; cin>>a>>b; mp[a][b]=1; mp[b][a]=1; } int q; cin>>q; while(q--) { memset(st,0,sizeof(st)); memset(s,0,sizeof(s)); int t=0; for
(int i=1;i<=n;i++) { cin>>a[i]; if(!s[a[i]]) { t++; s[a[i]]=1; } } if(t!=k) { cout<<"No"<<endl; continue; } f=1; for(int i=1;i<=n;i++) { if(!f) break; if(!st[i]) { st[i]=1; dfs(i); } } if(f) cout<<"Yes"<<endl; else cout<<"No"<<endl; } }

這個用了鄰接表來儲存以及搜尋

下面用鏈式向前星來記錄(不是自己寫的,自己寫的錯了QAQ問了某位大佬要的程式碼)

#include <iostream>
#include<cstring>
using namespace std;
const int N =1e6;
int e[N],ne[N],h[N],idx,clo[N];
bool st[N],flag,st1[N];
void add(int a,int b)
{
    e[idx]=b;
    ne[idx]=h[a];
    h[a]=idx++;
    
}
void dfs(int u)
{
    if(flag)return ;
    
    if(st[u])return;
    st[u]=1;
    for(int i=h[u];i!=-1;i=ne[i])
    {
        if(clo[u]==clo[e[i]])
        {
            flag=1;
            return ;
        }
        if(!st[e[i]])
            dfs(e[i]);
    }
    return ;
}
int main()
{
    memset(h,-1,sizeof h);
    int n,m,k;
    cin>>n>>m>>k;
    if(n==1)
    {
        cout<<"Yes"<<endl;
        return 0;
    }
    while(m--)
    {
        int a,b;
        cin>>a>>b;
        add(a,b);
        add(b,a);
    }
    int y;
    cin>>y;
    while(y--)
    {
        if(n==1)
        {
            cout<<"Yes"<<endl;
            continue;
        }
        memset(st,0,sizeof st);
        memset(st1,0,sizeof st1);
        flag=0;
        for(int i=1;i<=n;i++)
        {
            cin>>clo[i];
            st1[clo[i]]=1;
        }
        int s=0;
        for(int i=1;i<=1000;i++)if(st1[i])s++;
        if(s!=k)
        {
            cout<<"No"<<endl;
            continue;
        }
        for(int i=1;i<=n;i++)
        {
            if(!st[i])
                dfs(i);
        }
        if(flag) cout<<"No"<<endl;
        else cout<<"Yes"<<endl;
    }
    return 0;
    
}

還可以直接暴力,也是問了某位大佬QAQ,但自己又寫一遍23分,還有2分不知道

#include<iostream>
#include<vector>
#include<set>
using namespace std;
const int N=550;
vector<int> v[N];
int a[N];
set<int>q;
int n,m,k;
int main(){
    cin>>n>>m>>k;
    while(m--)
    {
        int a,b;
        cin>>a>>b;
        v[a].push_back(b);
        v[b].push_back(a);
    }
    int p;
    cin>>p;
    while(p--)
    {
        q.clear();
        for(int i=1;i<=n;i++)
        {
            cin>>a[i];
            q.insert(a[i]);
        }
        if(q.size()!=k)
        {
            cout<<"No"<<endl;
            continue;
        }
        int f=1;
        for(int i=1;i<=n;i++)
        {
            for(int j=1;j<=v[i].size();i++)
            {
                if(a[i]==a[v[i][j]])
                    f=0;
            }
        }
        if(f) cout<<"Yes"<<endl;
        else cout<<"No"<<endl; 
    }
    return 0;
}