#include <iostream> #include <stdio.h> #include <vector> #include <utility> #include <algorithm> using namespace std; int t, n, w; int xx1, yy1, xx2, yy2; vector < pair <int, int> > poczatek; vector < pair <int, int> > docelowe; int wysokosc[50001]; int s_poczatek[50001]; int s_docelowe[50001]; int s_adres[50001]; int przedzial[131072]; void dodaj(int indeks, int wart); void aktualizuj(int indeks); void szukaj_maks(int L, int P, int a, int b, int indeks); int wyn_maks = 0; bool da_sie = true; int main() { scanf("%d", &t); for(int i = 0; i < t; i++) { scanf("%d", &n); scanf("%d", &w); for(int j = 0; j < n; j++) { scanf("%d", &xx1); scanf("%d", &yy1); scanf("%d", &xx2); scanf("%d", &yy2); if(xx2 >= xx1) poczatek.push_back(make_pair(xx1, j+1)); else poczatek.push_back(make_pair(xx2, j+1)); if(yy2 >= yy1) wysokosc[j+1] = yy2-yy1; else wysokosc[j+1] = yy1-yy2; } for(int j = 0; j < n; j++) { scanf("%d", &xx1); scanf("%d", &yy1); scanf("%d", &xx2); scanf("%d", &yy2); if(xx2 >= xx1) docelowe.push_back(make_pair(xx1, j+1)); else docelowe.push_back(make_pair(xx2, j+1)); } sort(poczatek.begin(), poczatek.end()); sort(docelowe.begin(), docelowe.end()); for(int j = 1; j <= n; j++) s_poczatek[j] = poczatek[j-1].second; for(int j = 1; j <= n; j++) s_docelowe[j] = docelowe[j-1].second; for(int j = 1; j <= n; j++) s_adres[s_poczatek[j]] = j-1; for(int j = 0; j < n; j++) dodaj(j, wysokosc[s_poczatek[j+1]]); for(int j = 1; j <= n; j++) { wyn_maks = 0; szukaj_maks(1, 65536, 0, s_adres[s_docelowe[j]], 1); dodaj(s_adres[s_docelowe[j]], 0); if(wyn_maks > w-wysokosc[s_docelowe[j]]) { da_sie = false; break; } } if(da_sie) printf("TAK\n"); else printf("NIE\n"); for(int j = 0; j < 131072; j++) przedzial[j] = 0; poczatek.clear(); docelowe.clear(); da_sie = true; } return 0; } void dodaj(int indeks, int wart) { przedzial[65536+indeks] = wart; aktualizuj((65536+indeks)/2); } void aktualizuj(int indeks) { if(indeks > 0) { przedzial[indeks] = max(przedzial[2*indeks], przedzial[2*indeks+1]); aktualizuj(indeks/2); } } void szukaj_maks(int L, int P, int a, int b, int indeks) { if(b >= L && b >= P && L >= a && P >= a) { if(przedzial[indeks] > wyn_maks) wyn_maks = przedzial[indeks]; } else if(min(b,P) >= max(a,L)) { szukaj_maks(L, L+(P-L)/2, a, b, 2*indeks); szukaj_maks(L+(P-L)/2+1, P, a, b, 2*indeks+1); } }
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 | #include <iostream> #include <stdio.h> #include <vector> #include <utility> #include <algorithm> using namespace std; int t, n, w; int xx1, yy1, xx2, yy2; vector < pair <int, int> > poczatek; vector < pair <int, int> > docelowe; int wysokosc[50001]; int s_poczatek[50001]; int s_docelowe[50001]; int s_adres[50001]; int przedzial[131072]; void dodaj(int indeks, int wart); void aktualizuj(int indeks); void szukaj_maks(int L, int P, int a, int b, int indeks); int wyn_maks = 0; bool da_sie = true; int main() { scanf("%d", &t); for(int i = 0; i < t; i++) { scanf("%d", &n); scanf("%d", &w); for(int j = 0; j < n; j++) { scanf("%d", &xx1); scanf("%d", &yy1); scanf("%d", &xx2); scanf("%d", &yy2); if(xx2 >= xx1) poczatek.push_back(make_pair(xx1, j+1)); else poczatek.push_back(make_pair(xx2, j+1)); if(yy2 >= yy1) wysokosc[j+1] = yy2-yy1; else wysokosc[j+1] = yy1-yy2; } for(int j = 0; j < n; j++) { scanf("%d", &xx1); scanf("%d", &yy1); scanf("%d", &xx2); scanf("%d", &yy2); if(xx2 >= xx1) docelowe.push_back(make_pair(xx1, j+1)); else docelowe.push_back(make_pair(xx2, j+1)); } sort(poczatek.begin(), poczatek.end()); sort(docelowe.begin(), docelowe.end()); for(int j = 1; j <= n; j++) s_poczatek[j] = poczatek[j-1].second; for(int j = 1; j <= n; j++) s_docelowe[j] = docelowe[j-1].second; for(int j = 1; j <= n; j++) s_adres[s_poczatek[j]] = j-1; for(int j = 0; j < n; j++) dodaj(j, wysokosc[s_poczatek[j+1]]); for(int j = 1; j <= n; j++) { wyn_maks = 0; szukaj_maks(1, 65536, 0, s_adres[s_docelowe[j]], 1); dodaj(s_adres[s_docelowe[j]], 0); if(wyn_maks > w-wysokosc[s_docelowe[j]]) { da_sie = false; break; } } if(da_sie) printf("TAK\n"); else printf("NIE\n"); for(int j = 0; j < 131072; j++) przedzial[j] = 0; poczatek.clear(); docelowe.clear(); da_sie = true; } return 0; } void dodaj(int indeks, int wart) { przedzial[65536+indeks] = wart; aktualizuj((65536+indeks)/2); } void aktualizuj(int indeks) { if(indeks > 0) { przedzial[indeks] = max(przedzial[2*indeks], przedzial[2*indeks+1]); aktualizuj(indeks/2); } } void szukaj_maks(int L, int P, int a, int b, int indeks) { if(b >= L && b >= P && L >= a && P >= a) { if(przedzial[indeks] > wyn_maks) wyn_maks = przedzial[indeks]; } else if(min(b,P) >= max(a,L)) { szukaj_maks(L, L+(P-L)/2, a, b, 2*indeks); szukaj_maks(L+(P-L)/2+1, P, a, b, 2*indeks+1); } } |