掉分之旅…
前几场都打的比较顺,一直在上分,今天这场多半是掉分了…
赛后复盘,感觉这场其实还是挺简单的…其实每把都感觉有机会ak,这把感觉是机会最大的一次,然而…
希望下次能AK!!
t1 直接暴力 1A
t2 模拟 1A
t3 哈希+二分
t4 暴力打表/ 求下一个十进制回文数+进制转换
t3 我其实赛中有想过存下标来搜索,但是忘记加二分了…然后居然想去用二维vector的前缀和求,结果依然是tle 其实仔细想想,这题还蛮简单的,存出现下标,然后二分搜区间下标。
t4 暴力打表可以做。无奈t3耗时太长,最后打表到一半结束了,看了别人的打表,只能说我打表不够优雅。同时看了下其他大佬们的常规做法,学习了一手。
t3 5186. 区间内查询数字的频率 传送门
预处理每一个数出现的下标,然后二分查找应该查询的下标的位于什么位置
class RangeFreqQuery {
public:
RangeFreqQuery(vector<int>& arr) {
int n =arr.size();
for(int i=0;i<n;i++){
mp[arr[i]].push_back(i);
}
}
int query(int left, int right, int value) {
auto&x=mp[value];
int l = lower_bound(x.begin(),x.end(),left)-x.begin();
int r= upper_bound(x.begin(),x.end(),right)-x.begin();
return r-l;
}
unordered_map<int,vector<int>>mp;
};
/**
* Your RangeFreqQuery object will be instantiated and called as such:
* RangeFreqQuery* obj = new RangeFreqQuery(arr);
* int param_1 = obj->query(left,right,value);
*/
t4 k 镜像数字的和 传送门
暴力打表就不讲了
分为两步,一是求下一个回文十进制数,二是判断这个十进制数的k进制是否是回文的。
在求下一个回文十进制数中,我们需要从中间开始搜。这里的思想是,把回文数看成一个数的对称数字。比如说101101看成 101 对称复制一遍。这样我们搜回文数字的时候,只要改一遍就行了,比如101101的下一个,显然是102的回文,就是102201.
class Solution {
public:
typedef long long ll;
ll nextint(ll num){
string s=to_string(num);
int n = s.size();
for(int i=n/2;i>=0;i--){
if(s[i]!='9'){
s[i]++;
if(n-1-i!=i){
s[n-1-i]++;
}
for(int j=i+1;j<=n/2;j++){
s[j]='0';
s[n-1-j]='0';
}
return stoll(s); //转回数字
}
}
//如果上面的for循环没有通过,说明回文数字已经到最大,99999这种,就需要初始化为100001这种
ll ans=1;
for(int i=0;i<n;i++) ans*=10;
ans+=1;
return ans;
}
int check(ll num,int k){
ll ret=0;
ll p = num;
while(num){
ret*=k;
ret+=(num%k);
num/=k;
}
return ret==p;
}
long long kMirror(int k, int n) {
ll ans=0;
ll num=0;
while(n){
num = nextint(num); //求下一个十进制回文
if(check(num,k)==1){ //判断该十进制回文是否满足k进制回文
n--;
ans+=num;
}
}
return ans;
}
};
菜鸡落泪
希望下次能AK!!