packagecom.KongLong;importjava.util.Comparator;importjava.util.PriorityQueue;importjava.util.Queue;importjava.util.Scanner;classMoney
{int CurrentMoney;//当前费用;
int PossibleMoney;//当前结点可能最小的费用
int locat;//当前的行坐标
boolean vis[] = new boolean[25];
}class Cmp implements Comparator//优先级排序
{public intcompare(Money o1, Money o2)
{if(o1.PossibleMoney >o2.PossibleMoney)
{return 1;
}else if(o1.PossibleMoney ==o2.PossibleMoney)
{return 0;
}else{return -1;
}
}
}public classMain
{static intN;static final int MAX = 25;static int money[][] = new int[MAX][MAX];//邻接矩阵
static Money M[] = new Money[MAX];//在队列中使用
static int cnt = 0;static Queue que = new PriorityQueue(MAX,new Cmp());//优先队列
static intresult;public static voidmain(String []args)
{
init();
Scanner cin= newScanner(System.in);
N=cin.nextInt();
cnt= 0;
result= 99999999;for(int i = 0; i < N; i++)
{for(int j = 0; j < N; j++)
{
money[i][j]=cin.nextInt();
}
}for(int i = 0; i < N; i++)
{
M[cnt].CurrentMoney= money[0][i];
M[cnt].locat= 0;
M[cnt].vis[i]= true;
M[cnt].PossibleMoney= M[cnt].CurrentMoney+Bound(1);//System.out.println(M[cnt].PossibleMoney);
que.add(M[cnt]);
cnt++;
}while(!que.isEmpty())//队列为空判断
{
Money a= newMoney();
a=que.poll();//System.out.println(a.CurrentMoney + ">>>>>>> " + a.PossibleMoney + ">>> " + a.locat);
if(a.locat == N-1 && a.CurrentMoney < result)//界限
{
result=a.CurrentMoney;//System.out.println("000");
continue;
}else if(a.locat == N-1)//界限
{continue;
}else if(a.PossibleMoney > result)//剪枝
{break;
}for(int i = 0; i < N; i++)
{if(a.vis[i] == true)
{continue;
}
M[cnt].CurrentMoney= a.CurrentMoney+money[a.locat+1][i];
M[cnt].vis[i]= true;for(int j = 0; j < N; j++)
{if(a.vis[j] == true)
{
M[cnt].vis[j]= true;
}//System.out.println(M[cnt].vis[j]);
}
M[cnt].locat= a.locat+1;
M[cnt].PossibleMoney= M[cnt].CurrentMoney+Bound(a.locat+2);//System.out.println(M[cnt].CurrentMoney + " >>>>>>>>>>> " + M[cnt].PossibleMoney + " yyyyy ");//M[cnt].vis[i] = true;
que.add(M[cnt]);
cnt++;
}
}
System.out.println(result);
}static int Bound(int j)//当前结点的最小费用
{int sum = 0;for(int i = j; i < N; i++)
{int Min = 99999999;for(int k = 0; k < N; k++)
{if(M[cnt].vis[k] == true)
{//System.out.println(k + "k");
continue;
}
Min=Math.min(Min, money[i][k]);
}
sum+=Min;
}//System.out.println(j + "/ " + sum);
returnsum;
}static voidinit()
{for(int i = 0; i < MAX; i++)
{
M[i]= newMoney();
}
}
}
在写这段代码过程中,注意需要用一个数组保存队列,否则容易出现错误。