classSolution { intpermutation(int n, int m){ int ret = 1; for (int i = 0; i < n; i++) { ret *= m - i; } return ret; } public: intnumDupDigitsAtMostN(int N){ vector<int> digits; // transform N + 1 to list. Attention: have to be N + 1, not N int tmp = N + 1; while (tmp > 0) { digits.push_back(tmp % 10); tmp /= 10; } reverse(digits.begin(), digits.end()); int len = digits.size(); int ret = 0; // the first digit is 0 // take 3452 as an example // len = 4 // compute ***, **, * for (int i = 1; i < len; i++) { ret += 9 * permutation(len - i - 1, 9); } // the first digits is not 0 set<int> seen; for (int i = 0; i < len; i++) { // if i == 2 // compute 34** for (int j = ((i == 0) ? 1 : 0); j < digits[i]; j++) { // if j == 2 // compute 342* if (seen.find(j) == seen.end()) { ret += permutation(len - 1 - i, 10 - (i + 1)); } } // break if 344... if (seen.find(digits[i]) != seen.end()) break; seen.insert(digits[i]); } return N - ret; } };