zoukankan      html  css  js  c++  java
  • 回溯 分考场

    问题描述
      n个人参加某项特殊考试。
      为了公平,要求任何两个认识的人不能分在同一个考场。
      求是少需要分几个考场才能满足条件。
    输入格式
      第一行,一个整数n(1<n<100),表示参加考试的人数。
      第二行,一个整数m,表示接下来有m行数据
      以下m行每行的格式为:两个整数a,b,用空格分开 (1<=a,b<=n) 表示第a个人与第b个人认识。
    输出格式
      一行一个整数,表示最少分几个考场。
    样例输入
    5
    8
    1 2
    1 3
    1 4
    2 3
    2 4
    2 5
    3 4
    4 5
    样例输出
    4
    样例输入
    5
    10
    1 2
    1 3
    1 4
    1 5
    2 3
    2 4
    2 5
    3 4
    3 5
    4 5
    样例输出
    5
    正解
    #include<bits/stdc++.h>
    #define endl '
    '
    using namespace std;
    const int N = 1e2+5;
    typedef long long ll;
    int Vec[N][N];  //存放朋友,值为一是朋友 
    int Set[N][N];     //存放教室里的人
    int SetCnt[N];       //教室里的人数 
    int n,m,a,b;
    int res = 100; 
    void solve(int k,int q){  //开始处理第k个人,已经用了q个教室 
        if(q>=res){              //当现在安排的数量已经大于了最小的教室数量的话,返回
            return;
        }
        if(k>n){                 //安排的学生已经大于所有的学生了,就是安排完所有的学生了已经
            res=min(res,q);
            return;
        }
        
        for(int i=1;i<=q;i++){   //首先看看之前的房间i里面能不能放进去
            int KnowFlag = 0;
            int sz=SetCnt[i];//看看他熟悉的人在不在i房间 
            for(int j=1;j<=sz;j++){
                if(Vec[k][Set[i][j]]==1){
                    KnowFlag = 1;
                    break;  //有认识的人 
                }
            }
            if(KnowFlag==0){//这个房间可以放人 
                Set[i][ ++SetCnt[i] ] = k; //将这个学生存到这个考场中
                solve(k+1,q);
                SetCnt[i]--;
            }
        }
        //重新开一个房间
        Set[q+1][ ++SetCnt[q+1] ] = k; //将这个学生存到这个考场中
        solve(k+1,q+1);
        SetCnt[q+1]--;   
    } 
    int main(){
        ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
        // 用set存储每个教室的人  用vector存储每个人的熟悉的人  
        cin>>n>>m; 
        // n个人m个关系
        for(int i = 0;i<m; i++) {
            cin>>a>>b;
            Vec[a][b] = Vec[b][a] = 1; 
        }
        solve(1,1);  
        cout<<res<<endl;
        return 0;
    }
    用stl的vector和set超时了,比赛的时候看不到结果,还是能手写尽量手写吧(80分代码)
    #include<bits/stdc++.h>
    #define endl '
    '
    using namespace std;
    const int N = 1e2+5;
    typedef long long ll;
    vector<int> Vec[N];
    set<int> Set[N]; 
        int n,m,a,b;
    int res = 100; 
    void solve(int k,int q){  //开始处理第k个人,已经用了q个教室 
        if(q>=res){              //当现在安排的数量已经大于了最小的教室数量的话,返回
            return;
        }
        if(k>n){                 //安排的学生已经大于所有的学生了,就是安排完所有的学生了已经
            res=min(res,q);
            return;
        }
        int sz=Vec[k].size();//看看他熟悉的人在不在i房间 
        for(int i=1;i<=q;i++){   //首先看看之前的房间i里面能不能放进去
            int KnowFlag = 0;
            for(int j=0;j<sz;j++){
                if(Set[i].count( Vec[k][j] )){
                    KnowFlag = 1;
                    break;  //有认识的人 
                }
            }
            if(KnowFlag==0){//这个房间可以放人 
                Set[i].insert(k); //将这个学生存到这个考场中
                solve(k+1,q);
                Set[i].erase(k);
            }
        }
        //重新开一个房间
        Set[q+1].insert(k); //将这个学生存到这个考场中
        solve(k+1,q+1);
        Set[q+1].erase(k);  
    } 
    int main(){
        ios::sync_with_stdio(0),cin.tie(0),cout.tie(0);
        // 用set存储每个教室的人  用vector存储每个人的熟悉的人  
        cin>>n>>m; 
        // n个人m个关系
        for(int i = 0;i<m; i++) {
            cin>>a>>b;
            Vec[a].push_back(b);
            Vec[b].push_back(a); 
        }
        solve(1,1);  
        cout<<res<<endl;
        return 0;
    }
  • 相关阅读:
    JSP第六次作业
    JSP第五次作业
    第二次软件测试作业
    JSP第四次作业(2)
    JSP第四次作业(1)
    JSP第七次作业
    JSP第六次作业
    session对象练习
    JSP第四次作业(2)
    JSP第四次作业(1)
  • 原文地址:https://www.cnblogs.com/SunChuangYu/p/13812888.html
Copyright © 2011-2022 走看看