401. 二进制手表
思路:枚举时针的所有情况,已经秒针的所有情况。
代码:
#include<stdio.h>
class Solution {
public:
vector<string> readBinaryWatch(int turnedOn) {
int line1[] = {8 , 4 , 2 , 1} ;
int line2[] = {32 , 16 , 8 , 4 , 2 , 1} ;
vector<vector<int>> V1(100 , vector<int>()) , V2(100 , vector<int>()) ;
for (int i = 0 ; i < (1 << 4) ; ++i) {
int cnt = 0 ;
int now = 0 ;
for (int j = 0 ; j < 4 ; ++j) {
if (i & (1 << j)) {
++cnt ;
now += line1[j] ;
}
}
if (now <= 11) {
V1[cnt].push_back(now) ;
}
}
for (int i = 0 ; i < (1 << 6) ; ++i) {
int cnt = 0 ;
int now = 0 ;
for (int j = 0 ; j < 6 ; ++j) {
if (i & (1 << j)) {
++cnt ;
now += line2[j] ;
}
}
if (now <= 59) {
V2[cnt].push_back(now) ;
}
}
vector<string> res ;
for (int i = 0 ; i <= turnedOn ; ++i) {
int j = turnedOn - i ;
for (int k = 0 ; k < V1[i].size() ; ++k) {
string now_res ;
char tmp[100] ;
sprintf(tmp , "%d" , V1[i][k]) ;
now_res += tmp ;
now_res += ":" ;
for (int u = 0 ; u < V2[j].size() ; ++u) {
sprintf(tmp , "%02d" , V2[j][u]) ;
res.push_back(now_res+tmp) ;
}
}
}
return res ;
}
};
78. 子集
https://leetcode.cn/problems/subsets/description/
思路:直接暴力枚举所有情况即可
代码:
class Solution {
public:
vector<vector<int>> subsets(vector<int>& nums) {
vector<vector<int>> res ;
int n = nums.size() ;
for (int i = 0 ; i < (1 << n) ; ++i) {
vector<int> V ;
for (int j = 0 ; j < n ; ++j) {
if (i & (1 << j)) {
V.push_back(nums[j]) ;
}
}
res.push_back(V) ;
}
return res ;
}
};
46. 全排列
思路:用搜索的思路去遍历就好。STL有个很方便的东西next_permutation可以直接遍历
代码:
class Solution {
public:
vector<vector<int>> permute(vector<int>& nums) {
vector<vector<int>> res ;
sort(nums.begin() , nums.end()) ;
res.push_back(nums) ;
while (next_permutation(nums.begin() , nums.end())) {
res.push_back(nums) ;
}
return res ;
}
};
22. 括号生成
https://leetcode.cn/problems/generate-parentheses/description/
思路:n的最大数量为8,那么字符串长度最长是16,且是8个左括号,8个右括号构成的。只需要全排列,然后判断其中哪些是符合要求的字符串即可。
代码:
bool check(string str) {
int cnt = 0 ;
for (int i = 0 ; i < str.size() ; ++i) {
if (str[i] == '(') {
++cnt ;
}
else {
--cnt ;
if (cnt < 0) {
return false ;
}
}
}
return true ;
}
class Solution {
public:
vector<string> generateParenthesis(int n) {
string now = "" ;
for (int i = 0 ; i < n ; ++i) {
now += '(' ;
}
for (int i = 0 ; i < n ; ++i) {
now += ')' ;
}
sort(now.begin() , now.end()) ;
vector<string> res ;
while (true) {
if (check(now)) {
res.push_back(now) ;
}
if (next_permutation(now.begin() , now.end())) {
continue ;
}
else {
break ;
}
}
return res ;
}
};
17. 电话号码的字母组合
https://leetcode.cn/problems/letter-combinations-of-a-phone-number/
思路:
有点像全排列,也是去全排列组合
代码:
void solve(vector<string>& s , string& digits , int id , vector<string>& res , string& now) {
if (id == digits.size()) {
res.push_back(now) ;
return ;
}
int yoho = (digits[id] - '0') ;
for (int i = 0 ; i < s[yoho - 2].size() ; i++) {
now += s[yoho - 2][i] ;
solve(s , digits , id + 1 , res , now) ;
now.pop_back() ;
}
}
class Solution {
public:
vector<string> letterCombinations(string digits) {
string str = "" ;
for (int i = 0 ; i < 26 ; ++i) {
str += ('a' + i) ;
}
vector<int>l (10 , 3) ;
vector<string> s ;
l[7] = 4 ;
l[9] = 4 ;
int cnt = 0 ;
vector<string> res ;
if (digits == "") {
return res ;
}
for (int i = 2 ; i <= 9 ; ++i) {
s.push_back(str.substr(cnt , l[i])) ;
cnt += l[i] ;
}
string now = "" ;
solve(s , digits , 0 , res , now) ;
return res ;
}
};
89. 格雷编码
https://leetcode.cn/problems/gray-code/description/
思路:用了动态规划的思想。因为上一轮的是有效的,那么下一轮在上一轮的基础上补上一位就ok了,只需要上一轮的正序和上一轮的倒叙加前导1就可以了。
代码:
class Solution {
public:
vector<int> grayCode(int n) {
vector<vector<int>> res ;
vector<int> now ;
res.push_back(now) ;
now.push_back(0) ;
now.push_back(1) ;
res.push_back(now) ;
for (int i = 2 ; i <= 16 ; ++i) {
now.clear() ;
for (int j = 0 ; j < res[i - 1].size() ; ++j) {
now.push_back(res[i - 1][j]) ;
}
for (int j = res[i - 1].size() - 1 ; j >= 0 ; --j) {
now.push_back((1 << (i - 1)) + res[i - 1][j]) ;
}
res.push_back(now) ;
}
return res[n] ;
}
};
93. 复原 IP 地址
思路:枚举每个点的位置,然后判断是否满足条件
代码:
vector<string> now ;
vector<string> res ;
void dfs(string& s , int id , int cnt) {
if (cnt == 4) {
string yoho = "" ;
for (int i = 0 ; i < now.size() ; ++i) {
yoho += "." ;
yoho += now[i] ;
}
yoho = yoho.substr(1) ;
res.push_back(yoho) ;
return ;
}
if (cnt == 3) {
string nowstr = s.substr(id) ;
int nowint = atoi(nowstr.c_str()) ;
if (nowint > 255) {
return ;
}
string newstr = to_string(nowint) ;
if (nowstr != newstr) {
return ;
}
now.push_back(nowstr) ;
dfs(s , id , cnt + 1) ;
now.pop_back() ;
}
else
for (int i = 1 ; i + id < s.size() ; ++i) {
string nowstr = s.substr(id , i) ;
int nowint = atoi(nowstr.c_str()) ;
if (nowint > 255) {
continue ;
}
string newstr = to_string(nowint) ;
if (nowstr != newstr) {
continue ;
}
now.push_back(nowstr) ;
dfs(s , id + i , cnt + 1) ;
now.pop_back() ;
}
}
class Solution {
public:
vector<string> restoreIpAddresses(string s) {
int n = s.size() ;
now.clear() ;
res.clear() ;
dfs(s , 0 , 0) ;
return res ;
}
};
357. 统计各位数字都不同的数字个数
思路:对于长度为4的数字,第一位可以选9种,1~9。第二位可以选择9种,0以及1~9排除第一位,第三位可以选择8种,依次类推。
代码:
class Solution {
public:
int countNumbersWithUniqueDigits(int n) {
if (n == 0) return 1 ;
int res = 0 ;
for (int i = n ; i >= 1 ; --i) {
if (i == 1) {
res += 10 ;
continue ;
}
int a = 9 ;
int b = 9 ;
for (int j = 0 ; j < i - 1 ; ++j) {
a *= b ;
b-- ;
}
res += a ;
}
return res ;
}
};