难度简单49
给定两个正整数
x
和y
,如果某一整数等于x^i + y^j
,其中整数i >= 0
且j >= 0
,那么我们认为该整数是一个强整数。返回值小于或等于
bound
的所有强整数组成的列表。你可以按任何顺序返回答案。在你的回答中,每个值最多出现一次。
示例 1:
输入:x = 2, y = 3, bound = 10 输出:[2,3,4,5,7,9,10] 解释: 2 = 2^0 + 3^0 3 = 2^1 + 3^0 4 = 2^0 + 3^1 5 = 2^1 + 3^1 7 = 2^2 + 3^1 9 = 2^3 + 3^0 10 = 2^0 + 3^2示例 2:
输入:x = 3, y = 5, bound = 15 输出:[2,4,6,8,10,14]
提示:
1 <= x <= 100
1 <= y <= 100
0 <= bound <= 10^6
这题的暴力解法是超时的,因此需要另辟蹊径。我没有想到这题用这种方式,感觉自己算法解题的思路还是很欠缺。
这题用数组分别存储x, y的幂次方,然后对两个数组里面的元素进行加和,在bound范围内加入到结果数组中。开辟了两个数组空间来存储。
总结一下:
对这种以幂次方运算的算法题,往往暴力破解是会超时 n^n,那么用数组存储并计算幂次方即(n)
class Solution {
public:
vector<int> powerfulIntegers(int x, int y, int bound) {
vector<int>res;
if(bound < 2){
return res;
}
vector<int> xv, yv;
xv.push_back(1);
yv.push_back(1);
int a = x;
int b = y;
while(a < bound && a != 1){
xv.push_back(a);
a = a*x;
}
while(b != 1 && b < bound){
yv.push_back(b);
b = b*y;
}
for(int i: xv){
for(int j: yv){
if(i + j <= bound){
res.push_back(i+j);
}else{
break;
}
}
}
sort(res.begin(), res.end());
vector<int>::iterator pos = unique(res.begin(), res.end());
res.erase(pos, res.end());
// set<int> s(res.begin(), res.end());
// res.assign(s.begin(), s.end());
return res;
}
};
另外,这题我还学到了将数组转换成集合,即去重,然后再对集合转换成数组。
而通过搜索资料,我还找到了另外的一些针对数组去重的办法,用到了unique函数和erase函数
unique函数
返回值:去重以后vector中没有重复元素的下一个位置的迭代器pos。
应该说是重新排序了,因此需要将pos到end的所有重复元素抹去即可。
vector<int> v{3,4,5,1,2,5,3};
//排序
sort(v.begin(), v.end());
//1 2 3 3 4 5 5
//pos是去重以后vector中没有重复元素的下一个位置的迭代器。
vector<int>::iterator pos = unique(v.begin(), v.end());
//去重后整个容器
for (int i = 0; i < v.size(); i++)
{
cout << v[i] << ' ';
}
cout << endl;
//1 2 3 4 5 5 5
//从容器开始到pos:去重后的容器元素
for (vector<int>::iterator i = v.begin(); i < pos; i++)
{
cout << *i << ' ';
}
cout << endl;
//1 2 3 4 5
//从pos到容器结束:无意义的元素
for (vector<int>::iterator i = pos; i < v.end(); i++)
{
cout << *i << ' ';
}
cout << endl;
//5 5