Rucksackproblem (Knapsack)
Verfasst: So Mai 13, 2012 11:10 pm
Hallo Leute,
Es gibt hier diese schöne Beschreibung des Rucksackproblems: http://www.proggen.org/doku.php?id=algo:knapsack
Der dynamische Algorithmus macht was er soll und ich habe die Theorie weitestgehend verstanden, auch wenn ich manchmal noch stark nachdenken muss
Mein Problem ist, dass ich nicht nur wissen möchte was am Ende der größte Wert ist, sondern auch welche Gegenstände genau nun im Rucksack sind. Müsste doch eigentlich recht einfach sein rauszufinden wessen Werte letztendlich zusammen addiert worden sind.
Ich hab schon einiges hin und her probiert, finde aber keine Lösung.
Hat jemand vielleicht einen Tipp für mich?
Hier noch mal der C-Code:
Es gibt hier diese schöne Beschreibung des Rucksackproblems: http://www.proggen.org/doku.php?id=algo:knapsack
Der dynamische Algorithmus macht was er soll und ich habe die Theorie weitestgehend verstanden, auch wenn ich manchmal noch stark nachdenken muss

Mein Problem ist, dass ich nicht nur wissen möchte was am Ende der größte Wert ist, sondern auch welche Gegenstände genau nun im Rucksack sind. Müsste doch eigentlich recht einfach sein rauszufinden wessen Werte letztendlich zusammen addiert worden sind.
Ich hab schon einiges hin und her probiert, finde aber keine Lösung.

Hat jemand vielleicht einen Tipp für mich?
Hier noch mal der C-Code:
Code: Alles auswählen
#include <stdio.h>
// currentVolume: Das restliche (freie) Volumen im Rucksack
// i: Aktueller Gegenstand
// Return value: Maximaler Wert mit bzw. ohne den aktuellen Gegenstand
int knapsack( const int currentVolume, const int i );
// Maximale Anazahl an Gegenständen
const int maxN = 300;
// Maximales Volumen des Rucksacks
const int maxV = 1000;
// Anzahl an Byte für unseren Dynamisierungs-Array
const int resultLength = ( maxV + 1 ) * sizeof( int );
// Volumen des Rucksacks
int V;
// Anzahl an Gegenständen
int n;
// Volumen der einzelnen Gegenstände
int v[maxN];
// Werte der einzelnen Gegenstände
int w[maxN];
// Gespeicherte Ergebnisse von bisherigen Berechnungen
int results[maxN][maxV + 1];
int main()
{
// Eingabe der Daten
printf("Eingabe [Volumen Rucksack] [Anzahl Gegenstaende]:\n");
fscanf( stdin, "%d %d", &V, &n );
for( int i = 0; i < n; i++ ){
printf("\n%d. Gegenstaend: [Volumen] [Wert]\n", i+1);
fscanf( stdin, "%d %d", &( v[i] ), &( w[i] ) );
}
// Initialisierung des Dynamisierungs-Arrays
for( int i = 0; i < n; i++ )
memset( results[i], -1, resultLength );
// Berechnung und Ausgabe
fprintf( stdout, "\n%d\n", knapsack( V, 0 ) );
return 0;
}
int max(int a, int b)
{
return (a < b) ? b : a;
}
int knapsack( const int currentVolume, const int i )
{
// Prüfen, ob ein gültiger Index übergeben wurde
if( i < n )
{
// Prüfen, ob der Wert bereits berechnet wurde.
if( results[i][currentVolume] != -1 ){
return results[i][currentVolume];
}
// Berechne Wert ohne den aktuellen Gegenstand
int a = knapsack( currentVolume, i + 1 );
// Berechne Wert mit dem aktuellen Gegenstand, wenn noch Platz dafür ist
int b = 0;
if( currentVolume - v[i] >= 0 ){
b = w[i] + knapsack( currentVolume - v[i], i + 1 );
}
// Maximum der Berechnung wird gespeichert und zurückgegeben
results[i][currentVolume] = max(a, b);
return results[i][currentVolume];
}
return 0;
}