Online Judge | Problem Set | Authors | Online Contests | User | ||||||
---|---|---|---|---|---|---|---|---|---|---|
Web Board Home Page F.A.Qs Statistical Charts | Current Contest Past Contests Scheduled Contests Award Contest |
天啊!用离散化+线段树怎么也过不了!离散化直接暴力居然188ms过了!麻烦大侠帮忙看看线段树的代码!#include <stdio.h> int posters[10000][2]; int total, utotal; int nums[20000]; int unique(int); int search(int); typedef struct _snode { short who; short a; short b; } node; node nodes[32800];//这个数字测试过的9999时,最大为32725 #define LEFT(x) (((x) + 1) * 2 - 1) #define RIGHT(x) (((x) + 1) * 2) void create_tree(int, int, int); void free_tree(void); void place(int, int, int, int); int getresult(void); int comp(const void *, const void *); int main(int argc, char *argv[]) { int n, i; node *pn; scanf("%d", &n); while ( n-- > 0 ) { scanf("%d", &total); for ( i = 0; i < total; ++i ) { scanf("%d%d", &posters[i][0], &posters[i][1]); nums[2*i] = posters[i][0]; nums[2*i+1] = posters[i][1]; } qsort(nums, 2*total, sizeof(int), comp); utotal = unique(2*total); for ( i = 0; i < total; ++i ) { posters[i][0] = search(posters[i][0]); posters[i][1] = search(posters[i][1]); // printf("%d %d\n", posters[i][0], posters[i][1]); } if ( utotal == 1 ) { printf("1\n"); continue; } free_tree(); create_tree(0, 0, utotal - 1); for ( i = 0; i < total; ++i ) place(0, i, posters[i][0], posters[i][1]); printf("%d\n", getresult()); } return 0; } int comp(const void *left, const void *right) { return *(int*)left - *(int*)right; } void create_tree(int ni, int a, int b) { if ( ni < 0 || ni >= sizeof nodes / sizeof nodes[0] || b - a < 0 ) return; nodes[ni].a = a; nodes[ni].b = b; if ( b - a > 0 ) { create_tree(LEFT(ni), a, (a+b)/2); create_tree(RIGHT(ni), (a+b)/2 + 1, b); } } void free_tree(void) { int i; for ( i = 0; i < sizeof nodes / sizeof nodes[0]; ++i ) { nodes[i].a = nodes[i].b = 0; nodes[i].who = -1; } } void place(int ni, int who, int a, int b) { int tmp, mid; if ( ni < 0 || ni >= sizeof nodes / sizeof nodes[0] || a > b ) return; if ( nodes[ni].a > b || nodes[ni].b < a ) return; if ( nodes[ni].a >= a && nodes[ni].b <= b ) nodes[ni].who = who; else if ( nodes[ni].b == nodes[ni].a )//leaf return; else if ( b <= (mid = (nodes[ni].a + nodes[ni].b) / 2) ) { place(LEFT(ni), who, a, b); if ( nodes[ni].who != -1 ) { tmp = nodes[ni].who; nodes[ni].who = -1; place(ni, tmp, b + 1, nodes[ni].b); } } else if ( a >= mid + 1 ) { place(RIGHT(ni), who, a, b); if ( nodes[ni].who != -1 ) { tmp = nodes[ni].who; nodes[ni].who = -1; place(ni, tmp, nodes[ni].a, a - 1); } } else { place(LEFT(ni), who, a, b); place(RIGHT(ni), who, a, b); if ( nodes[ni].who != -1 ) { tmp = nodes[ni].who; nodes[ni].who = -1; place(ni, tmp, nodes[ni].a, a - 1); place(ni, tmp, b + 1, nodes[ni].b); } } } int getresult(void) { void see(int); int i, res; for ( i = 0; i < total; ++i ) nums[i] = 0; see(0); for ( i = res = 0; i < total; ++i ) res += nums[i]; return res; } void see(int ni) { if ( ni < 0 || ni >= sizeof nodes / sizeof nodes[0] ) return; if ( nodes[ni].who != -1 ) nums[nodes[ni].who] = 1; else if ( nodes[ni].b - nodes[ni].a > 0 ) { see(LEFT(ni)); see(RIGHT(ni)); } } int unique(int size) { int i, next; for ( i = next = 0; i < size; ++i, ++next) { while ( i + 1 < size && nums[i] == nums[i+1] ) ++i; if ( next != i ) nums[next] = nums[i]; } return next; } int search(int value) { int low, high, mid; low = 0; high = utotal - 1; while ( low <= high ) { mid = (low + high) / 2; if ( nums[mid] == value ) break; else if ( nums[mid] < value ) low = mid + 1; else high = mid - 1; } return low <= high ? mid : -1; } Followed by: Post your reply here: |
All Rights Reserved 2003-2013 Ying Fuchen,Xu Pengcheng,Xie Di
Any problem, Please Contact Administrator