最小总和问题(数字三角形)C++实现

问题描述

将正整数排成等边三角形,三角形的底边有n个数。从三角形顶点出发通过一系列相邻整数,使得达到底边时的总和最小(或最大)。
当n=4时,例子如下:
总和最小为14,路径为2 -> 5 -> 1 -> 6

在这里插入图片描述
以下思路和算法实现参考自:数字三角形(动态规划)–算法学习

思路

先把最后一行写入新的n×n的二维数组中。再看原数组中第n-1行的第一个数1,比较它在三角形中加上左下角的数得到的结果小还是加上右下角的数得到的结果小,即比较1+8小还是1+6小。显然是1+6小,则将结果7写入新数组的同一个位置中。
在这里插入图片描述
类似的,可获得新数组第n-1行的所有元素。
在这里插入图片描述
遍历到原数组的第n-2行,就比较原数组中第n-2行的元素加上它在新数组中相应位置的左下角和右下角的数值哪个更小,并写入到相应的位置。如第n-2行的第一个元素5,比较5+7小还是5+10小。显然是5+7小,则将结果12写入。
在这里插入图片描述
最后可得到一个完整的新数组,而新数组的第一个元素值即为最小总和。而再从新数组的第一个元素起往下推,找左下角和右下角中小的那一个,即可在原数组的相应位置获得路径上的元素。如:
新数组中第一个数为14,路径的开始的数则为原数组的2;
14的左下角12小于右下角14,则路径中加入原数组的5;
12的左下角7小于右下角10,则路径中加入原数组的1;
7的左下角8大于右下角6,则路径中种加入原数组的6。
在这里插入图片描述

算法实现

#include<iostream>

using namespace std;

#define MAX 101
int N[MAX][MAX];  //存放等边三角形,上述思路中的原数组
int minSum[MAX][MAX];  //存放路径和,上述思路中的新数组
int n;  //底边的数字个数

int main()
{
    cout<<"输入三角形底边数字个数:";
    cin>>n;

    //初始化,我的二维数组是从[1][1]开始的
    cout<<"输入数字构建等边三角形:";
    for(int i=1;i<=n;i++)
    {
        for(int j=1;j<=i;j++)
        {
            cin>>N[i][j];
        }
    }

    //将原数组的第n行写入新数组
    for(int j=1;j<=n;j++)
    {
        minSum[n][j]=N[n][j];
    }

    //从下往上遍历,构建新数组
    for(int i=n-1;i>=1;i--)
    {
        for(int j=1;j<=i;j++)
        {
            //min()函数不知道为啥用不了,暂时没解决,所以这里就用三元运算符了
            int temp=minSum[i+1][j]<=minSum[i+1][j+1? minSum[i+1][j] : minSum[i+1][j+1];
            minSum[i][j]=+N[i][j]+temp;
        }
    }

    //新数组的第一个元素即为最小总和
    cout<<"总和最小为:"<<minSum[1][1]<<endl;

    //从上往下遍历,找到新数组与原数组中对应的元素,并输出。k为上一行的路径元素所在的列
    cout<<"路径:";
    cout<<N[1][1]<<" ";
    int k=1;
    for(int i=2;i<=n;i++)
    {
       if(minSum[i][k]<=minSum[i][k+1])
       {
           cout<<N[i][k]<<" ";
       }
       else
       {
           cout<<N[i][k+1]<<" ";
           k=k+1;
       }
    }
    return 0;
}

在这里插入图片描述
p.s.代码还有很多不足,朋友们有需要就自行修改,如果有问题也麻烦帮我指出来!

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值