[Programación dinámica] 01 Problema de mochila: guerra de perros y gatos

Una pila de números se divide en dos grupos
(1) el número de cada grupo solo puede diferir en uno
(2) la diferencia entre la suma de cada grupo es lo más pequeña posible
Entrada: n, n números
Salida: la suma de cada grupo

01 Mochila:

La suma de todos los números es sum. Si desea que la suma de los dos conjuntos de números sea lo más pequeña posible, entonces los dos conjuntos de números deben estar lo más cerca posible de sum/2.


Si el número es par, elige n/2 números y la capacidad es suma/2, de modo que el valor sea el mayor. Si el
número es impar, elige n/2 números y la capacidad es suma/2, que es el mayor valor
Por lo tanto, entre los n números, elija n/2 números para que su suma sea la mayor y no exceda suma/2

dp[i][j][k]: Seleccione k números de los primeros i números para que su suma no supere j y el máximo
dp[i][j][k]=max(dp[i-1][ j] [k],dp[i-1][jw[i]][k-1]+w[i])
matriz rodante:
dp[j][k]=max(dp[j][k], dp[ jw[i]][k-1]+w[i]) 

código

#include<iostream>
#include<cstring>
using namespace std;
int n;
int w[201];
int dp[10000][201];
int main()
{
	memset(dp,0,sizeof(dp));
	cin>>n;
	int sum=0;
	for(int i=1;i<=n;i++){
		cin>>w[i];
		sum+=w[i];
	}
	for(int i=1;i<=n;i++)
	{
		for(int j=sum/2;j>=w[i];j--){
			for(int k=1;k<=n/2;k++){
				dp[j][k]=max(dp[j][k],dp[j-w[i]][k-1]+w[i]);
			}
		}
	}
	cout<<dp[sum/2][n/2];
}

Supongo que te gusta

Origin blog.csdn.net/m0_52043808/article/details/123978251
Recomendado
Clasificación