动态规划算法--币值最大化(c++实现)

动态规划算法--币值最大化(c++实现)


币值最大化的问题描述如下:给定n个硬币,其面值均为正整数c1,c2,…,cn,请问如何选择硬币,使得在其原始位置互不相邻的条件下,所选硬币的总金额最大,并且找出组成最大币值所包含的所有硬币!

解题思路分析:
  1.最大金额用F(n)表示,然后找到F(n)的递推关系,我们可以分成两组:一组是包含最后一个硬币的,另一组是不包含最后一个硬币的。

2.那第一组:F(n) = cn+F(n-2);//第n个币包含

第二组:F(n) = F(n-1);//第n个币不包含

即 F(n)=max{cn+F(n-2),F(n-1)},n>1 //比较两种情况并取较大值

3.再结合初始条件:F(0)=0(下标从1开始)0,F(1)=c1

获取最大币值的中心函数如下:

int coinmax(int n)
	{
		c[0] = 0;//初始化c[0]及f[0]
		f[0] = 0;
		f[1] = c[1];  //f[]中保存了计算过的每一步的值

		for (int i = 2; i <= n; i++)
		{
			f[i] = max(c[i] + f[i - 2], f[i - 1]);
				//获取最大币值

		}
		return f[n];
	}

完整实现代码如下:

#include <iostream>
#define MAX 20
int c[MAX];//存放各个币值的数组,下标0不用
int f[MAX];

    int max(int x,int y)  //取较大值函数
    {
        return (x>y)?x:y;
    }

	int coinmax(int n)
	{
		c[0] = 0;//初始化c[0]及f[0]
		f[0] = 0;
		f[1] = c[1];  //f[]中保存了计算过的每一步的值

		for (int i = 2; i <= n; i++)
		{
			f[i] = max(c[i] + f[i - 2], f[i - 1]);
				//获取最大币值

		}
		return f[n];
	}

	int main()
	{

		int n;
		printf("请输入有多少个纸币:");
		scanf("%d", &n);
		printf("请分别输入纸币的价值:");
		for (int i = 1; i <= n; i++)
		{
			scanf("%d", &c[i]);

		}
		int arr[MAX];//定义arr数组表示所选择的硬币
		int num = 0;
		printf("最大币值为:%d\n", coinmax(n));
		for (int i = n; i >= 1; i--)
		{
			if (f[i] == f[i - 1])//选择了第i-1个,然后再将第i-1个放进arr数组
			{
				arr[num++] = c[--i];

			}

			else{
				arr[num++] = c[i--];//没有选择第i-1个则将他本身先放入数组,
				               //然后再将数组c的下标减一,arr的下标加一
			}

		}
		printf("各个币值为:");
		for (int i = 0; i<num; i++)

			printf("%d ", arr[i]);




	}
;

实现效果:
在这里插入图片描述

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值