1.9 高效率的安排见面会

1.9 高效率的安排见面会

基本问题:在校园招聘的季节里,为了能让学生们更好地了解微软亚洲研究院各研究组的情况,HR部门计划为每一个研究组举办一次见面会,让各个研究组的员工能跟学生相互了解和交流。已知有n位学生,他们分别对m个研究组中的若干个感兴趣。为了满足所有学生的要求,HR希望每个学生都能参加自己感兴趣的所有见面会。如果每个见面会的时间为t,那么,如何安排才能够使得所有见面会的总时间最短? 最简单的办法,就是把m个研究组的见面会时间依次排开,那我们就要用m * t的总时间,我们有10多个研究小组,时间会拖得很长,能否进一步提高效率?

解法:将问题转化为图的模型进行,将每场招聘会假想成一个图中的节点,有学生同时参加两个招聘会,就将两个节点相连,最终得到一个完整的图,那么不想连的图肯定是可以同时举办的,也就节省了总的时间。如何求出这些不相连的节点呢,这就需要再一次转化,将求不直接相连节点问题转化为求图的最少着色问题,显然,同一种颜色的节点肯定是不想连的。这就转化成了图的最少着色问题。即图的最少着色问题

拓展问题

拓展问题1

  • 面试的时候,每次会面都有一个开始时间b[i] 和 结束时间e[i] 。
  • 现在有一组面试时间数据,现在要求每一个有冲突的时间,都不允许安排在同一个地点,求出最小需要安排的地点数目。

解法:

  • 解法1:也可以通过染色问题解决
  • 解法2:区间合并问题

拓展问题2 让每一个同学感兴趣的见面会尽可能的集中

解法:同学对见面会的兴趣度可以理解为图中的边的权重,让每个都集中也就是总体集中顶点着色数量设计好后,顶点起始时间排序,起始时间相同则按照上一顶点与欲选择顶点的兴趣度排序,最后得到结果

All Coding

// 1.9 高效率的安排见面会
import java.util.*;
class Test{
	static List<List<Integer>> graph;
	static int[] colored;
	public static void main(String[] args) {
		/**
		基础问题:在校园招聘的季节里,为了能让学生们更好地了解微软亚洲研究院各研究组的情况,HR部门计划为每一个研究组举办一次见面会,让各个研究组的员工能跟学生相互了解和交流(如图1-4所示)。已知有n位学生,他们分别对m个研究组中的若干个感兴趣。为了满足所有学生的要求,HR希望每个学生都能参加自己感兴趣的所有见面会。如果每个见面会的时间为t,那么,如何安排才能够使得所有见面会的总时间最短? 最简单的办法,就是把m个研究组的见面会时间依次排开,那我们就要用m * t的总时间,我们有10多个研究小组,时间会拖得很长,能否进一步提高效率?
		> 解法:
		将问题转化为图的模型进行,将每场招聘会假想成一个图中的节点,有学生同时参加两个招聘会,就将两个节点相连,最终得到一个完整的图,那么不想连的图肯定是可以同时举办的,也就节省了总的时间。如何求出这些不相连的节点呢,这就需要再一次转化,将求不直接相连节点问题转化为求图的最少着色问题,显然,同一种颜色的节点肯定是不想连的。这就转化成了图的最少着色问题。
			即图的最少着色问题
		
		*/
		int n= 3;
		int[][] paths = new int[][]{{1,2},{2,3},{3,1}};
		System.out.println(minColors(n,paths).length);
		int[][] intervals = {{1,3},{2,6},{8,10},{15,18},{22,24}};
		System.out.println(merge(intervals).length);
        
		
	}
	public static int[] minColors(int n, int[][] paths) {
        graph = new LinkedList<List<Integer>>();
        colored = new int[n+1];
        for(int i = 0;i<n+1;i++) graph.add(new LinkedList<Integer>());
        for(int[] info:paths){
            graph.get(info[0]).add(info[1]);
            graph.get(info[1]).add(info[0]);
        }
        for(int i = 1;i<n+1;i++) dfs(i);
        int[] res = new int[n];
        for(int i = 0;i < n;i++) res[i] = colored[i+1];
        return res;

    }
    public static void dfs(int n){
        if(colored[n] != 0) return;
        int[] record = new int[5];
        for(int node:graph.get(n)) record[colored[node]]=1;
        for(int i = 0;i<record.length;i++) if(record[i]==0) colored[n]=i;
        for(int node:graph.get(n)){
            dfs(node);
        }

    }
	/**
		拓展问题:
		拓展问题1:(1)  面试的时候,每次会面都有一个开始时间b[i] 和 结束时间e[i] 。
 				  (2)  现在有一组面试时间数据,现在要求每一个有冲突的时间,都不允许安排在同一个地点,求出最小需要安排的地点数目。 
		> 解法
			解法1:也可以通过染色问题解决
			解法2:区间合并问题
		拓展问题2:让每一个同学感兴趣的见面会尽可能的集中
			解法:同学对见面会的兴趣度可以理解为图中的边的权重,让每个都集中也就是总体集中顶点着色数量设计好后,顶点起始时间排序,起始时间相同则按照上一顶点与欲选择顶点的兴趣度排序,最后得到结果

	*/
	/**
	拓展问题1:就是典型的合并区间问题
	*/
	public static int[][] merge(int[][] intervals) {
        if (intervals.length == 0) {
            return new int[0][2];
        }
        Arrays.sort(intervals,(o1,o2)->(o1[0] - o2[0]));
        List<int[]> merged = new ArrayList<int[]>();
        for (int i = 0; i < intervals.length; ++i) {
            int L = intervals[i][0], R = intervals[i][1];
            if (merged.size() == 0 || merged.get(merged.size() - 1)[1] < L) {
                merged.add(new int[]{L, R});
            } else {
                merged.get(merged.size() - 1)[1] = Math.max(merged.get(merged.size() - 1)[1], R);
            }
        }
        return merged.toArray(new int[merged.size()][]);
    }
    /**
    拓展问题2:
    	同学对见面会的兴趣度可以理解为图中的边的权重,让每个都集中也就是总体集中顶点着色数量设计好后,顶点起始时间排序,起始时间相同则按照上一顶点与欲选择顶点的兴趣度排序,最后得到结果


    */
}
posted @ 2020-12-02 10:32  BOTAK  阅读(90)  评论(0编辑  收藏  举报