矩阵链乘法(最小乘法数) (动态规划算法实现)算法导论p201

 

#include<stdio.h>
#define MAX 99999999
int sign[10][10];
int min[10][10];
void print_optimal_parens(int i,int j)
{
 if(i==j)
 {
  printf("A%d",i);
  return ;
 }
 else
 {
  printf("(");
  print_optimal_parens( i,sign[i][j]);
  print_optimal_parens( sign[i][j]+1,j);
  printf(")");
 }
}

int RECURSIVE_MAXRIX_CHAIN(int p[],int i,int j)
{  
 int k,q;
 if(i==j)
  return 0;
 min[i][j]=MAX;
 
 for(k=i;k<=j-1;k++)
 {
  q=RECURSIVE_MAXRIX_CHAIN(p,i,k)+RECURSIVE_MAXRIX_CHAIN(p,k+1,j)+p[i-1]*p[k]*p[j];
  if(q<min[i][j])
  {
   min[i][j]=q;
   sign[i][j]=k;
  }
 }
 return min[i][j];
}

void MAXRIXE_CHAIN(int n,int p[])
{  
 int l,i,j,k,q;
 for(i=1;i<=n;i++)
  for(j=1;j<=n;j++)
  min[i][j]=sign[i][j]=0;
 for(i=1;i<=n;i++)//单个矩阵的乘法数位0 因此min的对角线都只为0
  min[i][i]=0;
 for(l=2;l<=n;l++)//矩阵链中 每l连续矩阵链的最小值
 {
  for(i=1;i<=n-l+1;i++)
  {
   j=i+l-1;
   min[i][j]=MAX;
   for(k=i;k<=j-1;k++)
   {
    q=min[i][k]+min[k+1][j]+p[i-1]*p[k]*p[j];//  p[i-1]*p[k]*p[j]是在矩阵Ai和Aj之间的k位置插入乘号
    if(q<=min[i][j])
    {
     min[i][j]=q;
     sign[i][j]=k;
    }
   }
  }
 }
}

void print(int n)
{
 int i,j;
 printf("min==%d\n",min[1][n]);
 for(i=1;i<=n;i++)
 {
  for(j=1;j<=n;j++)
   printf("%6d ",min[i][j]);
  printf("\n");
 }
 printf("\n");

 for(i=1;i<=n;i++)
 {
  for(j=1;j<=n;j++)
   printf("%d ",sign[i][j]);
  printf("\n");
 }
 printf("\n");
 print_optimal_parens(1,n);
 printf("\n");
}


int LOOKUP_CHAIN(int p[],int i,int j)
{
 int q,k;
 if(min[i][j]<MAX)
  return min[i][j];
 if(i==j)
  min[i][j]=0;
 else
  for(k=i;k<=j-1;k++)
  {
   q=LOOKUP_CHAIN(p,i,k)+LOOKUP_CHAIN(p,k+1,j)+p[i-1]*p[k]*p[j];
   if(q<min[i][j])
   {
    min[i][j]=q;
    sign[i][j]=k;
   }
  }
  return min[i][j];
}

void MEMOIZED_MATRIX_CHAIN(int n,int p[])
{
 int i,j;
 for(i=1;i<=n;i++)
  for(j=i;j<=n;j++)
   min[i][j]=MAX;

  LOOKUP_CHAIN(p,1,n);
}


 
 
int main()
{   freopen("1.txt","r",stdin);
 int n,i,flag;
 int p[10];
 
 printf("请输入矩阵链中矩阵的个数n:\n");
 scanf("%d",&n);
 printf("请输入矩阵链中矩阵的行列数:\n");
 
 for(i=0;i<=n;i++)
  scanf("%d",&p[i]);

 printf("输入1-直接递归求解\n输入2-用动态规划求解,即自底向上方法求解\n输入3 子问题通过查找备忘录的形式求解\n");
 scanf("%d",&flag);
 printf("flag==%d\n",flag);
    
  if(flag==1)
     RECURSIVE_MAXRIX_CHAIN(p,1,n);
  else if(flag==2)
  MAXRIXE_CHAIN(n,p);
  else
  MEMOIZED_MATRIX_CHAIN(n,p);

  print(n); 
 return 0;
}


 

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

gdliweibing

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值