• [POI2001]Goldmine


    Description

    Byteman作为Byteland的The Goldmine(某一公司厂矿)的最有功的雇员之一,即将在年末退休。为了表示对他的
    认真勤恳的工作的承认,The Goldmine的管理层愿意奖励他一小块长方形的矿地,此矿地长和宽为s和w且平行于坐
    标系统的轴线。长方形矿地的位置可由他自己选。当然,这块地的价值会随着位置的不同而不同。其价值是指这块
    区域内天然金矿石的数量(若矿石位于这块地的边缘,我们同样认为他是属于这个区域的)。你们的任务是计算出
    这块地的最大可能价值(即:为它选择最佳位置)。为简便起见,我们假定整个金矿的矿区是无穷的,但含有天然
    金矿石的区域却是有限的。
    要求
    写一程序:
    1、 读入天然金矿石的位置;
    2、 计算这块地的最大可能价值(即:求给定大小的这块地所含的天然金矿石的最大数);
    3、 输出结果

    Input

    第一行为俩正整数s、w,1<=s,w<=10 000,各自代表着此矩形区域平行X轴和Y轴的边的长度。第二行是一正整数n
    ,1<=n<=15 000,它表示此金矿矿区内天然矿石的数量。接下来的n行,每行为俩用单个空格隔开的整数x、y,-30
    000<=x,y<=30 000,它门分别表示了某一天然金矿石的X坐标和Y坐标。

    Output

    应恰有一整数,表示此块给定大小的矿地的最高价值。

    Sample Input
    1 2
    12
    0 0
    1 1
    2 2
    3 3
    4 5
    5 5
    4 2
    1 4
    0 5
    5 0
    2 3
    3 2

    Sample Output
    4


    这题同样可以用到扫描线的思想
    对于每个矿点,它可以向上下左右四个方向延伸,但这并不代表每个点就要考虑四个方向
    考虑下如果该点往下有一个最优解,那么下面的某个点必定有向上的最优解,所以我们只考虑每个矿点的两个方向
    扫描线在扫描的过程中,如果有矿区离它的距离超过了s(长),就把它踢掉,扫到的点加进来,点在加进来的时候向上方延伸w(宽),操作完之后取(max)即可

    #include<cmath>
    #include<cstdio>
    #include<cstring>
    #include<iostream>
    #include<algorithm>
    #define inf 0x7f7f7f7f
    using namespace std;
    typedef long long ll;
    typedef unsigned int ui;
    typedef unsigned long long ull;
    inline int read(){
    	int x=0,f=1;char ch=getchar();
    	for (;ch<'0'||ch>'9';ch=getchar())	if (ch=='-')	f=-1;
    	for (;ch>='0'&&ch<='9';ch=getchar())  x=(x<<1)+(x<<3)+ch-'0';
    	return x*f;
    }
    inline void print(int x){
    	if (x>=10)	 print(x/10);
    	putchar(x%10+'0');
    }
    const int N=1.5e4,limit=3e4;
    struct AC{
    	int x,y;
    	void join(){x=read(),y=read();}
    	bool operator <(const AC &a)const{return x<a.x;}
    }A[N+10];
    struct Segment{
    	#define ls (p<<1)
    	#define rs (p<<1|1)
    	int tree[limit*8+10],Lazy[limit*8+10];
    	void add_tag(int p,int v){Lazy[p]+=v,tree[p]+=v;}
    	void pushdown(int p){
    		if (!Lazy[p])   return;
    		add_tag(ls,Lazy[p]),add_tag(rs,Lazy[p]);
    		Lazy[p]=0;
    	}
    	void updata(int p){tree[p]=max(tree[ls],tree[rs]);}
    	void change(int p,int l,int r,int x,int y,int t){
    		if (x<=l&&r<=y){
    			add_tag(p,t);
    			return;
    		}
    		int mid=(l+r)>>1;
    		pushdown(p);
    		if (x<=mid)  change(ls,l,mid,x,y,t);
    		if (y>mid)   change(rs,mid+1,r,x,y,t);
    		updata(p);
    	}
    }T;
    int main(){
    	int s=read(),w=read(),n=read(),ans=0;
    	for (int i=1;i<=n;i++)   A[i].join();
    	sort(A+1,A+1+n);
    	for (int i=1,j=1;i<=n;i++){
    		while (A[j].x<A[i].x-s)  T.change(1,-limit,limit,A[j].y,min(A[j].y+w,limit),-1),j++;
    		//踢掉过远的点
    		T.change(1,-limit,limit,A[i].y,min(A[i].y+w,limit),1);//加进当前的点,向上延伸
    		ans=max(ans,T.tree[1]);
    	}
    	printf("%d
    ",ans);
    	return 0;
    }
    
  • 相关阅读:
    python脚本 – 删除指定天数前的文件
    java 获取屏幕的分辩率
    解决Multi input/output stream coders are not yet supported(org.apache.commons.compress)
    解决tomcat at org.apache.tomcat.util.buf.CharChunk.append(CharChunk.java:355)
    org.quartz.jobStore.misfireThreshold = 60000
    python list 自定义排序
    利用pycron在windows上实现cron定时任务
    [Selenium+Java] Scroll UP or Down a page in Selenium Webdriver
    Python获取硬件信息(硬盘序列号,CPU序列号)
    ChromeDriver自动更新、FirefoxDriver自动更新、InternetExplorerDriver自动更新(Java+Python)
  • 原文地址:https://www.cnblogs.com/Wolfycz/p/8414586.html
Copyright © 2020-2023  润新知