fork download
  1. <?php
  2.  
  3.  
  4. $bills = Array(10, 50, 100, 200, 500, 1000, 2000); // какие виды банкнот есть
  5. $countOfBills = count($bills); // кол-во видов банкнот
  6. $needleMoney = 6600; // сумма которую надо выдать
  7.  
  8. // 1 часть алгоритма
  9. $INF = PHP_INT_MAX; //Бесконечность
  10. $F = Array(); //Массив вида: Требуемая сумма => Минимальное количество купюр для её выдачи
  11. $F[0] = 0; //Ноль гривен выдать нельзя
  12.  
  13. for ($i = 1; $i <= $needleMoney; ++$i) { //Флажок i идет от единицы до суммы, которую необходимо выдать
  14.  
  15. $F[$i] = $INF; //По умолчанию считаем что вывод невозможен
  16. for ($j = 0; $j < $countOfBills; ++$j) { //Массив проходит по всем банкнотам, его флажок j служит ключем для массива с банкнотами
  17. if ($i >= $bills[$j] && $F[$i - $bills[$j]] + 1 < $F[$i]) { /*Если $i больше чем текущая банкнота и
  18.   F[$i-ТекущаяБанкнота] +1 меньше чем количество банкнот для $i */
  19. $F[$i] = $F[$i - $bills[$j]] + 1; //Тогда определяется новое количество банкнот для $i, оно равно F[$i-ТекущаяБанкнота] +1
  20. }
  21. }
  22. }
  23.  
  24. // 2 часть алгоритма
  25. if ($F[$needleMoney] == $INF) { //Если количество купюр для выдачи необходимой суммы бесконечно
  26. echo "Требуемую сумму выдать невозможно\r\n"; // Выводим сообщение об этом
  27. } else { //В другом случае
  28. while ($needleMoney > 0) { //Пока необходимая сумма больше нуля
  29. for ($i = 0; $i < $countOfBills; ++$i) { //Цикл фор, в котором перебираются номиналы
  30. if ($F[$needleMoney - $bills[$i]] == $F[$needleMoney] - 1) { //Если F[Необходимая сумма МИНУС купюра данного номинала == F[Необходимая сума]-1 ]
  31. echo $bills[$i] . " "; //Выводим эту купюру
  32. $needleMoney -= $bills[$i]; //Минусуем от необходимой суммы купюру
  33. break; //Конец
  34. }
  35. }
  36. }
  37. }
Success #stdin #stdout 0.03s 24420KB
stdin
Standard input is empty
stdout
100 500 2000 2000 2000