Questo è un classico problema di programmazione dinamica (si noti prima che l'algoritmo greedy non funziona sempre qui!).
Assumere le monete sono ordinate in modo che a_1 > a_2 > ... > a_k = 1
. Definiamo un nuovo problema. Diciamo che il problema (i, j)
consiste nel trovare il numero minimo di monete che apportano modifiche per j
utilizzando monete a_i > a_(i + 1) > ... > a_k
. Il problema che vogliamo risolvere è (1, j)
per qualsiasi j
con 1 <= j <= n
. Supponi che C(i, j)
sia la risposta al problema (i, j)
.
Ora, considerare un'istanza (i, j)
. Dobbiamo decidere se stiamo usando o meno una delle monete a_i
. Se non lo siamo, stiamo solo risolvendo un problema (i + 1, j)
e la risposta è C(i + 1, j)
. Se lo siamo, completiamo la soluzione apportando modifiche per j - a_i
. Per fare ciò usando il minor numero possibile di monete, vogliamo risolvere il problema (i, j - a_i)
. Organizziamo le cose in modo che questi due problemi sono già risolti per noi e poi:
C(i, j) = C(i + 1, j) if a_i > j
= min(C(i + 1, j), 1 + C(i, j - a_i)) if a_i <= j
ora capire che cosa i primi casi sono e come tradurre questo per la lingua di vostra scelta e si dovrebbe essere a posto.
Se si desidera provare le mani a un altro problema interessante che richiede una programmazione dinamica, consultare Project Euler Problem 67.
Aiutare un ragazzo a risolvere un problema di compiti a casa non li farà improvvisamente diventare uno studente A +. In alcuni casi potrebbe aiutare lo studente a "vedere la luce" e diventare uno sviluppatore giovane e brillante. Qualcuno che ripete comunque il comportamento (non cercando di risolvere i problemi da solo) è più probabile che sia semplicemente qualcuno che non cresce mai perché non si sta sfidando da solo. Crolleranno e bruceranno miseramente ad un certo punto, molto probabilmente il giorno dell'esame. Almeno dove andavo a scuola, gli esami erano una percentuale così alta dei nostri voti che i compiti a casa erano effettivamente irrilevanti (in un corso gli esami erano al 100%). – jason