// 装配线调度.cpp : 定义控制台应用程序的入口点。 // #include "stdafx.h" #include <iostream> using namespace std; /* 动态规划,解决装配线问题(问题来自算法导论第15章) 作者:blackmamba 时间:2010年10月4日 */ /* a[i][j]表示在装配站Si,j上所需的装配时间i=1,2;1<=j<=n e[i],x[i]分别表示底盘进入装配线i的进入时间和离开时间 t[i][j]表示在装配站Si,j后,从一个装配线到另一个装配线的时间 fi[j]表示一个底盘从起点到装配站Si,j的最快可能时间1<=j<=n li[j]表示装配线的编号1或2,其中的装配站j-1被通过转配站Si,j的最快路线所用 2<=j<=n fmin表示最短时间的长度 line表示通过装配站n时的装配线 */ int a[3][7] = {{0, 0, 0, 0, 0, 0, 0}, {0, 7, 9, 3, 4, 8, 4}, {0, 8, 5, 6, 4, 5, 7}}; int e[3] = {0, 2, 4}; int x[3] = {0, 3, 2}; int t[3][6] = {{0, 0, 0, 0, 0, 0}, {0, 2, 3, 1, 3, 4}, {0, 2, 1, 2, 2, 1}}; int f[3][7]; int l[3][7]; int fmin; int line; void fastestWay(int a[3][7], int t[3][6], int e[], int x[], int n) { f[1][1] = e[1] + a[1][1]; f[2][1] = e[2] + a[2][1]; for (int i=2; i<=n; i++) { //一开始进入线路1 if ((f[1][i-1] + a[1][i]) <= (f[2][i-1] + t[2][i-1] + a[1][i])) { f[1][i] = f[1][i-1] + a[1][i]; l[1][i] = 1;//表示选择第1条线上的该点 } else { f[1][i] = f[2][i-1] + t[2][i-1] + a[1][i]; l[1][i] = 2;//表示选择第2条线上的该点 } //一开始进入线路2 if ((f[2][i-1] + a[2][i]) <= (f[1][i-1] + t[1][i-1] + a[2][i])) { f[2][i] = f[2][i-1] + a[2][i]; l[2][i] = 2; } else { f[2][i] = f[1][i-1] + t[1][i-1] + a[2][i]; l[2][i] = 1; } } if (f[1][n] + x[1] <= f[2][n] + x[2]) { //从线路1的第n个装配站出去时间段所以选择线路1 fmin = f[1][n] + x[1]; line = 1; } else { fmin = f[2][n] + x[2]; line = 2; } } void printStation(int l[3][7], int line, int n) { int i = line; printf("line %d, station %d/n", i, n); for (int j=n ; j>=2; j--) { i = l[i][j]; printf("line %d, station %d/n", i, j-1); } } int _tmain(int argc, _TCHAR* argv[]) { fastestWay(a, t, e, x, 6); printStation(l, line, 6); printf("最短时间为:%d/n", fmin); return 0; }