❤ (ɔˆз(ˆ⌣ˆc)“玥”——乃古上神珠也。见者好运连连,点个关注,咱们来玥方长!
(ง •̀_•́)ง加油😁😁😁
目录
❤ (ɔˆз(ˆ⌣ˆc)“玥”——乃古上神珠也。见者好运连连,点个关注,咱们来玥方长!
前言
电路布线问题与我们的生活息息相关,切合生活实际,为了使在同一层里布线最多,而线之间又不能相交,提出本问题。读者很好理解问题,理解问题是解决本题的关键!!!!
一、问题描述
在一块电路板的上、下两端分别有n个接线柱。根据电路设计,要求用导线(i,π(i)) 将上端接线柱i与下端接线柱π(i)相连,如下图。其中,π(i),1≤ i ≤n,是{1,2,…,n}的一个排列。导线(I, π(i))称为该电路板上的第i条连线。
一个例子:
对于任何1 ≤ i ≤ j ≤n,第i条连线和第j条连线相交的充要条件是π(i)> π(j).
在制作电路板时,要求将这n条连线分布到若干绝缘层上。换句话说,这个问题是要确定将哪些连线安排在第一层上,使得该层上有尽可能多的连线(不相交)。该问题要求确定导线集Nets = {i,π(i),1 ≤ i ≤ n}的最大不相交子集。
二、实现算法代码
/** * author;来玥方长 * Time:2022-4-24(日) * size[][]记录最长不相交子集的长度 * int c[]为下端导线接口 * net[] 记录最长不相交的连线情况 */ class MNS { public static void mnset(int[] c,int [][]size) //自底向上递归计算最优值算法 { int n=c.length-1; for(int j=0;j<c[1];j++) //对应第一种情况,i=1,j<c[1] size[1][j]=0; for(int j=c[1];j<=n;j++) //i=1,j>=c[1] size[1][j]=1; for(int i=2;i<n;i++) //对应第二种情况,i>1 { for(int j=0;j<c[i];j++) //j<c[i] size[i][j]=size[i-1][j]; for(int j=c[i];j<=n;j++) //j>=c[i] size[i][j]=Math.max(size[i-1][j],size[i-1][c[i]-1]+1); } size[n][n]=Math.max(size[n-1][n],size[n-1][c[n]-1]+1); //size最终取最大的长度 } /** * * @param c * @param size * @param net * @return */ public static int traceback(int []c,int [][]size,int []net) //构造最优解算法 { int n=c.length-1; int j=n; int m=0; for(int i=n;i>1;i--) { if(size[i][j] != size[i-1][j]) { net[m++]=i; j=c[i]-1; } } if(j>=c[1]) net[m++]=1; System.out.println("最大不相交子集连线分别为:"); for (int t = m - 1; t >= 0; t--) { System.out.println(net[t] + " " + c[net[t]]); } return m; } public static void main(String[]args) { int c[]={0,6,8,12,2,1,4,5,3,11,7,10,9,13}; //下标从1开始,开始元素为0不算 int size[][]=new int[c.length][c.length]; mnset(c, size); //计算最优值 int net[]=new int[c.length]; int m=traceback(c, size, net); //构造最优解 System.out.println("最长不相交子集长度为:"+m); } }
三、运行结果
总结
该问题比较简单,算法的设计过程就不详细解释了,通过认真看代码,可以理解问题的所在,多思考才是关键!!!