2019.11.12 星期二
今天我的消息队列又满了,继续肝作业!
今天基本写完了pa,调试一下,明天去找ta一波带走就完事儿了。
好吧,快回去了,虽然很想回去,但是还是得把事情干完,站好最后一班岗,大学即将过半,也许是当初许下的诺言还没有完成吧,没能打进regional,没能在所有课上拿A,遗憾太多了,不过能在这种情况下一个人静静地写代码,这样的日子还能有多久呢,不知道。
不感慨了,今天概率去找老师问题,结果老师跟我说这个是要求给定阿尔法值能装得下的最大值,这不是背包问题么,老师鬼魅的一笑,这种问题我自然是不可能用大脑思考出来的,于是乎回去打开clion写了个小程序就搞定了,同学一脸惊讶说你怎么这么快就算好了?我心想,废话,是我手速快罢了。然后就是莫队,我突然发现昨天写的是对的,我忽略了一个问题,就是莫队排序的时候需要用左右端点 / 块的大小然后进行暴力搜索,而网上很多大佬都是说2/3块的时候分的快,我就照着写了,结果给我卡住了。。。runtime error,我今天想了一天也没想出来,为了测试下这个算法究竟可不可行,我去网上找了份洛谷题解魔改了一下提交上去,发现我的猜想完全可行,那为什么会runtime error呢?
搞了半天原来是,万一n是1,2,3,我的大小就变成0了,然后就会出现除以0无穷大的情况,怪不得,改了之后提交,完美通过,又一个算法收入囊中,现在发现自己那场icpc会做的题已经有六道了,还差一道就能进nac了,加油加油!把那个最短路拿下我们就是最强的了。
排名进top10了,不错
下面放上题解
ICPC North America Mid Central Regional H 题 Farming Mars(传送门)
AC代码
#include <bits/stdc++.h>
using namespace std;
#define limit 110000 + 5//防止溢出
#define INF 0x3f3f3f3f
#define inf 0x3f3f3f3f3ff
#define lowbit(i) i&(-i)//一步两步
#define EPS 1e-6
#define ff(a) printf("%d\n",a );
#define MOD 1e9 + 7
typedef long long ll;
void read(int &x){
char ch = getchar();x = 0;
for (; ch < '0' || ch > '9'; ch = getchar());
for (; ch >='0' && ch <= '9'; ch = getchar()) x = x * 10 + ch - '0';
}//快读
struct Dbl{
double val;
Dbl(double vv = 0):val(vv){}
bool operator==(const Dbl &rhs)const{
return abs(val - rhs.val) <= 0.000001;
}
bool operator<(const Dbl &rhs)const{
return val < rhs.val;
}
};//哈哈我太聪明了
map<double, int>mapp;
int sum[limit], a[limit], cnt[limit],ans, res[limit];
struct Node{
int L, R ,first ,second;
Node():L(0) , R(1), first(0), second(0){}
bool operator<(const Node &rhs)const{
if(second ^ rhs.second){
return L < rhs.L;
}else {
if (second & 1) {
//如果是奇数
return R < rhs.R;
} else {
return R > rhs.R;
}
}
}
}query[limit];
struct answer{
int id, val;
bool operator<(const answer &rhs)const{
return val < rhs.val;
}
}value[limit];
int n, m , block;
void add(int x){
--sum[cnt[a[x]]];
++cnt[a[x]];
++sum[cnt[a[x]]];
ans = max(cnt[a[x]], ans);//比较
}
void del(int x){
--sum[cnt[a[x]]];
if(cnt[a[x]] == ans && !sum[cnt[a[x]]]){
--ans;//没有了
}
--cnt[a[x]];
++sum[cnt[a[x]]];
}
int t;
int diff[limit];
int main() {
//freopen("C:\\Users\\administrator01\\CLionProjects\\untitled14\\data.txt", "rt", stdin);
t = 0;
scanf("%d%d" , &n, &m);
for (int i = 1; i <= n; ++i) {
double d;
cin>>d;
if (mapp.find(d) == mapp.end()) {
//没找过
mapp[d] = ++t;
value[i].val = mapp[d];//如果找过了
value[i].id = i;
} else {
value[i].val = mapp[d];//如果找过了
value[i].id = i;
}//找过了
}
block = int(sqrt(n >= 3 ? n * (2.0 / 3) : n));//分块
sort(value + 1, value + 1 + n);
int index = 0;
a[value[1].id] = index;
for(int i = 2 ; i <= n ; ++i){
if(value[i].val != value[i - 1].val) ++index;
a[value[i].id] = index;
}
for(int i = 1 ; i <= m ; ++i){
scanf("%d%d" , &query[i].L, &query[i].R);
if(query[i].L > query[i].R){
swap(query[i].L , query[i].R);
}
query[i].first = i;
diff[i] = query[i].R - query[i].L + 1;
query[i].second = query[i].L / block;
}
sort(query + 1, query + m + 1);
int L = 1, R = 1;
ans = 1;
cnt[a[1]] = 1;
sum[1] = 1;
for(int i = 1 ; i <= m ; ++i){
if(query[i].R == query[i].L){
res[query[i].first] = 1;
continue;
}
while(L < query[i].L){
del(L++);
}
while(L > query[i].L){
add(--L);
}
while(R < query[i].R){
add(++R);
}
while(R > query[i].R){
del(R--);
}
res[query[i].first] = ans;
}
for(int i = 1 ; i <= m ; ++i){
int same = res[i];//取反
//printf("The %dth length of query is %d and the same number is %d\n",i, diff[i] , same );
if(same >= diff[i] / 2 + 1){
printf("usable\n");
}else{
printf("unusable\n");
}
}
return 0;
}