mirror of
https://github.com/ShusenTang/LeetCode.git
synced 2024-09-02 14:20:01 +00:00
44 lines
1.4 KiB
Markdown
44 lines
1.4 KiB
Markdown
![]() |
# [357. Count Numbers with Unique Digits](https://leetcode.com/problems/count-numbers-with-unique-digits/)
|
|||
|
|
|||
|
# 思路一
|
|||
|
|
|||
|
给定一个整数n,求范围[0,10^n]内有多少个各位上不均相同的数字,例如134这种。
|
|||
|
|
|||
|
这其实就是个数学题,我们考虑一下如何构造一个共i位且各位各不相同的数:
|
|||
|
* 先从0-9这10个数字中选取i个数字;
|
|||
|
* 再将选取的i个数字进行排列,需注意0不能排在最前面;
|
|||
|
|
|||
|
由高中数学排列组合知识知,从10个数选取i个再排列一共有A(10,i)种情况,再除去0排在前面的共A(9,i),所以最后一共有 A(10,i) - A(9,i) = 9*A(9, i-1)。
|
|||
|
> A(m, n) = m * (m-1) * ... * (m-n+1)
|
|||
|
|
|||
|
需要注意的是如果位数超过10那就没法组成每位都不相同的数了。
|
|||
|
|
|||
|
知道通项公式后,我们就可以根据n的大小,把[1, n]区间位数通过通项公式算出来累加起来即可。
|
|||
|
|
|||
|
|
|||
|
如果没想到数学解法,本题也可以直接进行搜索。
|
|||
|
|
|||
|
# C++
|
|||
|
``` C++
|
|||
|
// 此代码还可优化, 算阶乘那里重复计算了
|
|||
|
class Solution {
|
|||
|
private:
|
|||
|
int helper(int n){
|
|||
|
if(n == 0) return 1;
|
|||
|
if(n > 10) return 0;
|
|||
|
int res = 9;
|
|||
|
for(int i = 9; i > 9 - n + 1; i--)
|
|||
|
res *= i;
|
|||
|
return res;
|
|||
|
}
|
|||
|
public:
|
|||
|
int countNumbersWithUniqueDigits(int n) {
|
|||
|
int res = 0;
|
|||
|
for(int i = 0; i <= n; i++)
|
|||
|
res += helper(i);
|
|||
|
|
|||
|
return res;
|
|||
|
}
|
|||
|
};
|
|||
|
```
|