20201128 模拟赛总结

题目PDF,提取码 99bh

\(95+5+50+4=154\text{pts}\),rk3。

violet_holmes \(155\text{pts}\) rk2,差一分就离谱((

T1

模拟即可。

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<queue>
using namespace std;
bool a[110][110];
int main()
{
	queue<char> que;
	int hx=0,hy=0,tx=0,ty=0;
	int n,m,t,q;
	scanf("%d %d %d %d",&n,&m,&t,&q);
	for(int i=1;i<=t;i++)
	{
		int x,y;
		scanf("%d %d",&x,&y);
		a[x][y]=1;
	}
	int stx,sty;
	scanf("%d %d",&stx,&sty);
	hx=stx;hy=sty;
	a[hx][hy]=1; // 考试的时候没加这句话,挂了五分。。
	int i;
	for(i=1;i<=q;i++)
	{
		int pos;
		scanf("%d",&pos);
		if(pos==1)
		{
			char s[10];
			scanf("%s",s);
			if(s[0]=='R') hy++;
			else if(s[0]=='L') hy--;
			else if(s[0]=='U') hx--;
			else if(s[0]=='D') hx++;
			if(hx<1 || hx>n || hy<1 || hy>m) break;
			if(a[hx][hy]) break;
			a[hx][hy]=true;
			que.push(s[0]);
		}
		else
		{
			if(tx==0 && ty==0)
			{
				tx=stx;ty=sty;
				a[tx][ty]=0;
			}
			else
			{
				char c=que.front(); que.pop();
				if(c=='R') ty++;
				else if(c=='L') ty--;
				else if(c=='U') tx--;
				else if(c=='D') tx++;
				a[tx][ty]=0;
			}
		}
	}
	printf("%d",i>q?-1:i);
	return 0;
}

T2

原题:洛谷 P2123

推式子,详见这里

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
using namespace std;
const int N=20000;
struct node
{
	int a,b;
	node() {} 
}a[N+10];
bool cmp(node x,node y) {return min(x.a,y.b)==min(x.b,y.a)?x.a<y.a:min(x.a,y.b)<min(x.b,y.a);}
typedef long long ll;
int main()
{
	int T;
	scanf("%d",&T);
	while(T--)
	{ 
		int n;
		scanf("%d",&n);
		for(int i=1;i<=n;i++) scanf("%d %d",&a[i].a,&a[i].b);
		sort(a+1,a+n+1,cmp);
		ll sum=0,c=0;
		for(int i=1;i<=n;i++)
		{
			sum+=a[i].a;
			c=max(sum,c)+a[i].b;
		}
		printf("%lld\n",c);
	} 
	return 0;
}

T3

\(b_i\) 表示区间 \([i,n]\) 内比 \(a_i\) 小的数的个数,显然区间的逆序对个数就是 \(\sum_{i=1}^n b_i\)。根据题意,可以得到一个结论:若一个数 \(a_i\) 被取出(不论是如何被取出),\(b_i\) 都会变为 \(0\),不会对答案产生再产生贡献,然后我们就可以使用线段树去维护。

具体地,可以一开始算出区间逆序对个数 \(s=\sum_{i=1}^n b_i\),线段树维护 \(\{a_i\}\) 的区间最小值和最小值的下标,第 \(i\) 次操作操作取出区间 \([p_i,n]\) 的最小值 \(a_k\) 并将 \(a_k\) 设为极大值,同时 \(s\) 相对应地减去 \(b_k\),直到 \(a_k>a_{p_i}\) 为止。

代码实现有一些难度。

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
using namespace std;
const int N=5e5;
int a[N+10],d[N+10],b[N+10];
inline void read(int &x)
{
	x=0; int f=1;
	char c=getchar();
	while(c<'0' || c>'9')
	{
		if(c=='-') f=-1;
		c=getchar();
	}
	while(c>='0' && c<='9')
	{
		x=(x<<1)+(x<<3)+(c^48);
		c=getchar();
	}
	x*=f;
}
struct seg
{
	int l,r,min,pos;
}t[N*4+10];
void push_up(int p)
{
	if(t[p*2].min<t[p*2+1].min)
	{
		t[p].min=t[p*2].min;
		t[p].pos=t[p*2].pos;
	}
	else
	{
		t[p].min=t[p*2+1].min;
		t[p].pos=t[p*2+1].pos; 
	}
}
void build(int p,int l,int r)
{
	t[p].l=l;t[p].r=r;
	if(l==r)
	{
		t[p].min=a[l];
		t[p].pos=l;
		return;
	}
	int mid=(l+r)/2;
	build(p*2,l,mid);
	build(p*2+1,mid+1,r);
	push_up(p);
}
void modify(int p,int l,int d)
{
	if(t[p].l==t[p].r) 
	{
		t[p].min=d;
		return;
	}
	int mid=(t[p].l+t[p].r)/2;
	if(l<=mid) modify(p*2,l,d);
	else modify(p*2+1,l,d);
	push_up(p);
}
//first:value, second:position
pair<int,int> query(int p,int l,int r)
{
	if(l<=t[p].l && t[p].r<=r) return make_pair(t[p].min,t[p].pos);
	int mid=(t[p].l+t[p].r)/2;
	pair<int,int> ans=make_pair(0x7fffffff,0x7fffffff);
	if(l<=mid) ans=min(ans,query(p*2,l,r));
	if(r>mid) ans=min(ans,query(p*2+1,l,r));
	return ans;
}
int s;
int c[N+10];
void modify(int x,int d) {for(;x<=s;x+=x&-x) c[x]+=d;}
int query(int x)
{
	int ans=0;
	for(;x;x-=x&-x) ans+=c[x];
	return ans; 
}
typedef long long ll;
int main()
{
	int n,m;
	read(n);read(m);
	for(int i=1;i<=n;i++)
	{
		read(a[i]);
		d[i]=a[i];
	}
	sort(d+1,d+n+1);
	s=unique(d+1,d+n+1)-d-1;
	for(int i=1;i<=n;i++) a[i]=lower_bound(d+1,d+s+1,a[i])-d;
	ll ans=0;
	for(int i=n;i;i--)
	{
		b[i]=query(a[i]-1);
		ans+=b[i];
		modify(a[i],1);
	}
	build(1,1,n);
	for(int Case=1;Case<=m;Case++)
	{
		int p;
		read(p);
		while(1)
		{
			pair<int,int> tmp=query(1,p,n);
			if(tmp.first>a[p]) break;
			ans-=b[tmp.second];
			modify(1,tmp.second,0x7fffffff);
		}
		printf("%lld\n",ans);
	}
	return 0; 
}
/*
5 3
1 4 2 5 3 
5 2 4
*/

T4

弃了。

如果 NOIP 考这题我大概率输出随机数走人。

posted @ 2020-11-28 13:35  zzt1208  阅读(201)  评论(1编辑  收藏  举报