1. 程式人生 > >【POJ 2482】 Stars in Your Window(線段樹+離散化+掃描線)

【POJ 2482】 Stars in Your Window(線段樹+離散化+掃描線)

d+ opera algorithm ans som lov ble word wait

【POJ 2482】 Stars in Your Window(線段樹+離散化+掃描線)

Time Limit: 1000MS Memory Limit: 65536K
Total Submissions: 11294 Accepted: 3091

Description

Fleeting time does not blur my memory of you. Can it really be 4 years since I first saw you? I still remember, vividly, on the beautiful Zhuhai Campus, 4 years ago, from the moment I saw you smile, as you were walking out of the classroom and turned your head back, with the soft sunset glow shining on your rosy cheek, I knew, I knew that I was already drunk on you. Then, after several months’ observation and prying, your grace and your wisdom, your attitude to life and your aspiration for future were all strongly impressed on my memory. You were the glamorous and sunny girl whom I always dream of to share the rest of my life with. Alas, actually you were far beyond my wildest dreams and I had no idea about how to bridge that gulf between you and me. So I schemed nothing but to wait, to wait for an appropriate opportunity. Till now — the arrival of graduation, I realize I am such an idiot that one should create the opportunity and seize it instead of just waiting.

These days, having parted with friends, roommates and classmates one after another, I still cannot believe the fact that after waving hands, these familiar faces will soon vanish from our life and become no more than a memory. I will move out from school tomorrow. And you are planning to fly far far away, to pursue your future and fulfill your dreams. Perhaps we will not meet each other any more if without fate and luck. So tonight, I was wandering around your dormitory building hoping to meet you there by chance. But contradictorily, your appearance must quicken my heartbeat and my clumsy tongue might be not able to belch out a word. I cannot remember how many times I have passed your dormitory building both in Zhuhai and Guangzhou, and each time aspired to see you appear in the balcony or your silhouette that cast on the window. I cannot remember how many times this idea comes to my mind: call her out to have dinner or at least a conversation. But each time, thinking of your excellence and my commonness, the predominance of timidity over courage drove me leave silently.

Graduation, means the end of life in university, the end of these glorious, romantic years. Your lovely smile which is my original incentive to work hard and this unrequited love will be both sealed as a memory in the deep of my heart and my mind. Graduation, also means a start of new life, a footprint on the way to bright prospect. I truly hope you will be happy everyday abroad and everything goes well. Meanwhile, I will try to get out from puerility and become more sophisticated. To pursue my own love and happiness here in reality will be my ideal I never desert.

Farewell, my princess!

If someday, somewhere, we have a chance to gather, even as gray-haired man and woman, at that time, I hope we can be good friends to share this memory proudly to relight the youthful and joyful emotions. If this chance never comes, I wish I were the stars in the sky and twinkling in your window, to bless you far away, as friends, to accompany you every night, sharing the sweet dreams or going through the nightmares together.
技術分享

Here comes the problem: Assume the sky is a flat plane. All the stars lie on it with a location (x, y). for each star, there is a grade ranging from 1 to 100, representing its brightness, where 100 is the brightest and 1 is the weakest. The window is a rectangle whose edges are parallel to the x-axis or y-axis. Your task is to tell where I should put the window in order to maximize the sum of the brightness of the stars within the window. Note, the stars which are right on the edge of the window does not count. The window can be translated but rotation is not allowed.

Input

There are several test cases in the input. The first line of each case contains 3 integers: n, W, H, indicating the number of stars, the horizontal length and the vertical height of the rectangle-shaped window. Then n lines follow, with 3 integers each: x, y, c, telling the location (x, y) and the brightness of each star. No two stars are on the same point.

There are at least 1 and at most 10000 stars in the sky. 1<=W,H<=1000000, 0<=x,y<2^31.

Output

For each test case, output the maximum brightness in a single line.

Sample Input

3 5 4
1 2 3
2 3 2
6 3 1
3 5 4
1 2 3
2 3 2
5 3 1

Sample Output

5
6

Source

POJ Contest,Author:[email protected]


非常考察綜合應用的一個問題。。

反正我是卡了好久=.=

首先題目大意:天上有n顆星星(1 <= n <= 10000) 每一個星星有一個坐標 (x,y)(0 <= x , y < 2^31)和亮度 c(1 <= c <= 100)

你有一個矩形框 寬w 高h 問怎樣框能讓框裏的星星亮度和最大

另外在邊框上的星星的亮度不計入


直觀的看 沒什麽思路……我是沒思路…………………………………………暴力的話星星的選與不選會導致出現很多狀態 想都甭想+。

+

既然是分在線段樹專題 那就盡可能往線段樹靠唄。。。

線段樹是對區間查詢 但僅僅支持一維區間 這樣的二維區間僅僅能想辦法把一個維度限制 這樣 對於遍歷到某個x的時候 出如今全部y的需多個區間的亮度和就easy求了

固定x就須要用到掃描線了 通過排序 讓星星依照x有序 這樣掃描全部的x 每當掃到一個x就把星星的亮度增加相應的y區間內

但僅僅加亮度滿足了左邊界 還須要在超出w寬度限制的時候把最前面的星星亮度從區間中取走

也就是用到了掃描線拆分線段的方法 在起點把這個塊的價值增加 在終點減去 對於此題 起點是x 終點就是x+w 也就是從x最遠能碰觸到的邊框


這樣每一個點拆分成兩部分 一部分是起點亮度為正值 還有一個是終點 亮度相反 對於全部拆出的2*n個點排序 優先依照x排序 x同樣的價值為負的在前

由於要求邊框上的星星不計入 因此須要先把邊框上的星星亮度減去 再增加新星星


這樣對於x處理好了 從頭遍歷 每遍歷到一個點 就在y的區間內增加它的亮度(或正或負) y區間事實上就是[y,y+h-1] 就是它能夠貢獻價值的區間

可是y非常大 所以又涉及到一個離散化的問題 把全部出現過的y的值進行排序 然後離散化處理下就可以


不知道為什麽 G++總是RE。。。可能哪裏寫挫了?。

。有G++ A的大神 還是自己水平不夠啊~~。。


代碼例如以下:

#include <iostream>
#include <cmath>
#include <vector>
#include <cstdlib>
#include <cstdio>
#include <cstring>
#include <queue>
#include <stack>
#include <list>
#include <algorithm>
#include <map>
#include <set>
#define LL long long
#define Pr pair<int,int>
#define fread() freopen("in.in","r",stdin)
#define fwrite() freopen("out.out","w",stdout)

using namespace std;
const int INF = 0x3f3f3f3f;
const int msz = 10000;
const int mod = 1e9+7;
const double eps = 1e-8;

struct Star
{
	LL x,y1,y2,s;
	bool operator < (const struct Star a)const
	{
		return x == a.x? s < 0: x < a.x;
	}
};

LL sum[80004];
LL add[80004];
Star seg[20004];
LL ny[20004];
LL tp;
LL w,h;

void Update(LL root,LL l,LL r,LL y1,LL y2,LL d)
{
	//printf("l:%lld r:%lld\n",ny[l],ny[r]);
	if(ny[l] == y1 && ny[r] == y2)
	{
	//	printf("add:%lld",add[root]);
		add[root] += d;
	//	printf("->%lld\n",add[root]);

	//	printf("sum:%lld",sum[root]);
		sum[root] += d;
	//	printf("->%lld\n",sum[root]);
		return;
	}

	LL mid = (l+r)>>1;
	if(add[root])
	{
		sum[root<<1|1] += add[root];
		add[root<<1|1] += add[root];
		sum[root<<1] += add[root];
		add[root<<1] += add[root];
		add[root] = 0;
	}
	if(ny[mid] >= y2) Update(root<<1,l,mid,y1,y2,d);
	else if(ny[mid+1] <= y1) Update(root<<1|1,mid+1,r,y1,y2,d);
	else
	{
		Update(root<<1,l,mid,y1,ny[mid],d);
		Update(root<<1|1,mid+1,r,ny[mid+1],y2,d);
	}
	sum[root] = max(sum[root<<1],sum[root<<1|1]);
}

int main()
{
	//fread();
	//fwrite();

	LL n;

	while(~scanf("%lld%lld%lld",&n,&w,&h))
	{
		for(LL i = 1; i <= n; ++i)
		{
			scanf("%lld%lld%lld",&seg[i].x,&seg[i].y1,&seg[i].s);
			seg[i].y2 = seg[i].y1+h-1;

			seg[i+n] = seg[i];
			seg[i+n].x = seg[i].x+w;
			seg[i+n].s = -seg[i].s;

			ny[i] = seg[i].y1;
			ny[i+n] = seg[i].y2;
		}

		if(w == 0 || h == 0)
		{
			puts("0");
			continue;
		}
		sort(ny+1,ny+2*n+1);
		sort(seg+1,seg+2*n+1);
		tp = 0;
		for(LL i = 1; i <= 2*n; ++i)
			if(i == 1 || ny[i] != ny[i-1])
				ny[++tp] = ny[i];

		LL ans = 0;
		memset(sum,0,sizeof(sum));
		memset(add,0,sizeof(add));
		for(LL i = 1; i <= 2*n; ++i)
		{
		//	printf("%lld %lld\n",seg[i].y1,seg[i].y2);
			Update(1,1,tp,seg[i].y1,seg[i].y2,seg[i].s);
			ans = max(ans,sum[1]);
		}

		printf("%lld\n",ans);
	}

	return 0;
}





【POJ 2482】 Stars in Your Window(線段樹+離散化+掃描線)