我不关注是2枚硬币,还是3枚。
用回溯法求解:
#include <iostream> #include <vector> using namespace std; int array[] = {5, 4, 1}; const int size = sizeof array / sizeof *array; vector<vector<int> > ivecs; vector<int> ivec; void generateCandidates(int *array, int size, int index, int *candidates, int &ncandidate) { if (array == NULL || size <= 0) return; ncandidate = 0; for (int i = index; i < size; i++) { candidates[i - index] = array[i]; ncandidate++; } } bool isSolution(int sum) { if (sum == 0) return true; else return false; } void process(vector<vector<int> > &ivecs, vector<int> &ivec) { ivecs.push_back(ivec); } void process(int *array, int size, int *states, int &index, vector<vector<int> > &ivecs, vector<int> &ivec, int sum) { if (array == NULL || size <= 0 || states == NULL) return; if (sum < 0) { return; } int candidates[100]; int ncandidate; if (isSolution(sum) == true) process(ivecs, ivec); else { generateCandidates(array, size, index, candidates, ncandidate); for (int i = 0; i < ncandidate; i++) { sum -= candidates[i]; ivec.push_back(candidates[i]); for (int m = 0; m < size; m++) { if (array[m] == candidates[i]) index = m; } process(array, size, states, index, ivecs, ivec, sum); ivec.pop_back(); sum += candidates[i]; } } } void main() { int states[size]; int index = 0; int sum = 8; process(array, size, states, index, ivecs, ivec, sum); int minNumber = 65535; int pos; for (int i = 0; i < ivecs.size(); i++) { if (minNumber > ivecs[i].size()) { pos = i; minNumber = ivecs[i].size(); } } copy(ivecs[pos].begin(), ivecs[pos].end(), ostream_iterator<int>(cout, " ")); }
迭代算法简单易懂
#include <iostream> #include <vector> using namespace std; int array[] = {5, 4, 1}; const int size = sizeof array / sizeof *array; vector<vector<int> > ivecs; vector<int> ivec; void getCoins(int *array, int size, int total) { if (array == NULL || size <= 0) return; int leftIndex = 0; int rightIndex = 0; int totalCount = 0; int count = 0; int value = total; while (leftIndex != size) { while (rightIndex != size) { count = value / array[rightIndex]; if (count != 0) { for (int i = 0; i < count; i++) ivec.push_back(array[rightIndex]); } value = value % array[rightIndex]; rightIndex++; } if (value == 0) { ivecs.push_back(ivec); ivec.clear(); } leftIndex++; rightIndex = leftIndex; value = total; } int minNumber = 65535; int pos; for (int i = 0; i < ivecs.size(); i++) { if (minNumber > ivecs[i].size()) { pos = i; minNumber = ivecs[i].size(); } } copy(ivecs[pos].begin(), ivecs[pos].end(), ostream_iterator<int>(cout, " ")); } void main() { int sum = 38; getCoins(array, size, sum); }