字节编程题 毕业旅行问题

    科技2024-12-25  4

    小明目前在做一份毕业旅行的规划。打算从北京出发,分别去若干个城市,然后再回到北京,每个城市之间均乘坐高铁,且每个城市只去一次。由于经费有限,希望能够通过合理的路线安排尽可能的省一些路上的花销。给定一组城市和每对城市之间的火车票的价钱,找到每个城市只访问一次并返回起点的最小车费花销。

    输入描述: 城市个数n(1<n≤20,包括北京) 城市间的车票价钱 n行n列的矩阵 m[n][n] 输出描述: 最小车费花销 s 示例1 输入 4 0 2 6 5 2 0 4 4 6 4 0 2 5 4 2 0 输出 13 说明 共 4 个城市,城市 1 和城市 1 的车费为0,城市 1 和城市 2 之间的车费为 2,城市 1 和城市 3 之间的车费为 6,城市 1 和城市 4 之间的车费为 5,依次类推。假设任意两个城市之间均有单程票可购买,且票价在1000元以内,无需考虑极端情况。 import java.util.Scanner; public class Main { public static void main(String[] args) { Scanner in = new Scanner(System.in); int n = in.nextInt(); int[][] dist = new int[n][n]; for (int i = 0; i < dist.length; i++) { for (int j = 0; j < n; j++) { dist[i][j] = in.nextInt(); } } in.close(); //随便挑一个作为起点,为方便计算,就选择0城市就好, // 那么对应的事件可以理解为从0号城市出发去(1号、2号、3号城市)最后回到0号城市,其中中间的1、2、3之间的顺序不清楚怎么去的。 //但是可以发现事件最小消耗为min(从0->1的距离+从1号到{2号、3号}最后回到0的距离、 // 从0->2的距离+从2号到{1号、3号}最后回到0的距离、 // 从0->3的距离+从1号到{1号、2号}最后回到0的距离)。 // 用bit第几位是否为1表示当前事件有哪几号城市。{2号、3号}——> 110; int V = 1 << (n - 1); int[][] dp = new int[n][V]; dp[0][0] = 0; for (int j = 0; j < V; j++) { for (int i = 0; i < n; i++) { if (j == 0) { //表示从第i个城市到第j(0)个城市的最小路径。正好就是第i个城市去第0个城市的距离。 dp[i][j] = dist[i][j] + dp[0][0]; } else { dp[i][j] = Integer.MAX_VALUE; for (int k = 1; k < n; k++) { //表示第k位城市。 int index = (1 << (k - 1)); //当前的dp应该是遍历了j城市集的每一个城市对应的子dp+i到k的距离,求得的其中的最小的那个值; if ((index & j) > 0) { //找到其中的一个k; //表示j城市集内除了第k位其他的别的城市 int other = j ^ index; dp[i][j] = Math.min(dist[i][k] + dp[k][other], dp[i][j]); } } } } } System.out.println(dp[0][V - 1]); } }
    Processed: 0.062, SQL: 8