POJ 1695

直接DP,做完看别人说是用类似于双调欧几里得旅行商问题一样的方法解,仔细一看我的代码,貌似也和那旅行商问题做法差不多~~

这题坑爹之处在于,不能用floyd去优化,也就是说说好了从a到c是99,然后你不能靠先到b再到c来优化。。

View Code
 1 #include<cstdio>

 2 #include<cstring>

 3 #include<queue>

 4 using namespace std;

 5 int cos[50][50],dp[2][33][33][33];

 6 struct data

 7 {

 8     int x,y,z;

 9     data() {}

10     data(int _x,int _y,int _z)

11     {

12         x=_x;

13         y=_y;

14         z=_z;

15     }

16 }Q[200000];

17 int main()

18 {

19     int T;

20     for(scanf("%d",&T); T; T--)

21     {

22         int n;

23         scanf("%d",&n);

24         memset(cos,-1,sizeof(cos));

25         for(int i=1; i<n; i++)

26         {

27             cos[i][i]=0;

28             for(int j=i+1; j<=n; j++)

29             {

30                 scanf("%d",&cos[i][j]);

31                 cos[j][i]=cos[i][j];

32             }

33         }

34         cos[n][n]=0;

35         memset(dp,-1,sizeof(dp));

36         dp[0][1][1][1]=0;

37         int st,ed;

38         st=ed=0;

39         Q[ed++]=data(1,1,1);

40         for(int t=2; t<=n; t++)

41         {

42             int x=t&1,y=x^1;

43             int i=ed;

44             while(st!=i)

45             {

46                 data a=Q[st++];

47                 if(st==200000)

48                     st=0;

49                 int tp=dp[x][a.x][a.y][a.z];

50                 int fp=dp[y][t][a.y][a.z];

51                 if(fp==-1||fp>tp+cos[a.x][t])

52                 {

53                     dp[y][t][a.y][a.z]=tp+cos[a.x][t];

54                     if(fp==-1)

55                     {

56                         Q[ed++]=data(t,a.y,a.z);

57                         if(ed==200000)

58                             ed=0;

59                     }

60                 }

61                 fp=dp[y][a.x][t][a.z];

62                 if(fp==-1||fp>tp+cos[a.y][t])

63                 {

64                     dp[y][a.x][t][a.z]=tp+cos[a.y][t];

65                     if(fp==-1)

66                     {

67                         Q[ed++]=data(a.x,t,a.z);

68                         if(ed==200000)

69                             ed=0;

70                     }

71                 }

72                 fp=dp[y][a.x][a.y][t];

73                 if(fp==-1||fp>tp+cos[a.z][t])

74                 {

75                     dp[y][a.x][a.y][t]=tp+cos[a.z][t];

76                     if(fp==-1)

77                     {

78                         Q[ed++]=data(a.x,a.y,t);

79                         if(ed==200000)

80                             ed=0;

81                     }

82                 }

83             }

84             memset(dp[x],-1,sizeof(dp[x]));

85         }

86         int ans=1<<30,t=(n+1)&1;

87         while(st!=ed)

88         {

89             data tmp=Q[st++];

90             if(st==200000)

91                 st=0;

92             ans=min(ans,dp[t][tmp.x][tmp.y][tmp.z]);

93         }

94         printf("%d\n",ans);

95     }

96     return 0;

97 }

你可能感兴趣的:(poj)