1. 程式人生 > >已知n行資料,自上而下為第1行,第2行.....第n行。第i行資料有i個,求從第1行至第n行的最短路徑及路徑長度。

已知n行資料,自上而下為第1行,第2行.....第n行。第i行資料有i個,求從第1行至第n行的最短路徑及路徑長度。

#include <stdio.h>
//主函式
void main(){
int a[50][50];//儲存資料的陣列
int value[50][50];//儲存計算後的值
int sataus[50][50];//儲存分支的值
int min;//儲存最後一行中的最小值,用於排序
int i,j,b,value1,value2,ii,jj;
//輸入資料
printf("要輸入多少行資料?\n");
scanf("%d",&b);
for(i=0;i<b;i++){
printf("請輸入第%d行資料\n",i);
for(j=0;j<=i;j++){
scanf("%d",&a[i][j]);
}  
}


//將資料相加放入新樹組value
value[0][0]=a[0][0];//源點相等
sataus[0][0]=0;
for(i=1;i<b;i++)
for(j=0;j<=i;j++){
if(j==0){
     value[i][j]=value[i-1][j]+a[i][j];//第1列的數燈於value中同列上一行的數加上a中該行該列的數
sataus[i][j]=1;
}
else if(j==i){
                value[i][j]=value[i-1][j-1]+a[i][j];//三角形斜邊上的點
sataus[i][j]=2;
}
else{
value1=value[i-1][j-1]+a[i][j];
value2=value[i-1][j]+a[i][j];
if(value1<value2){
value[i][j]=value1;
sataus[i][j]=2;
}
else {
value[i][j]=value2;
sataus[i][j]=1;
}


}
                
}


//找出最短路徑
       min=value[b-1][0];
   ii=b-1;
   jj=0;
   for(j=1;j<b;j++)//找出最後一行的最小值
   if(min>value[b-1][j]){
               min=value[b-1][j];
   jj=j;
   }
for(i=b-1;i>=0;i--){
if(sataus[ii][jj]==1){
               sataus[ii][jj]=0;
   ii=i-1;
   jj=jj;
   
}
else if(sataus[ii][jj]==2){
               sataus[ii][jj]=0;
   ii=i-1;
   jj=jj-1;
   
}
           }


//輸出
for(i=0;i<b;i++){
for(j=0;j<=i;j++){
printf("%d",sataus[i][j]);
printf("\t");
}
printf("\n");
}
}