# | Time | Username | Problem | Language | Result | Execution time | Memory |
---|---|---|---|---|---|---|---|
1159529 | Doncho_Bonboncho | Treasure (different grader from official contest) (CEOI13_treasure2) | C++20 | 0 ms | 0 KiB |
#include <bits/stdc++.h>
#include <stdio.h>
#include <assert.h>
#include <stdlib.h>
#include <string.h>
#include "treasure.h"
#define out( x ) #x << " = " << x << " "
#ifndef LOCAL
#define cerr if(false) cerr
#endif
using namespace std;
typedef long long ll;
struct State{
int x1, y1;
int x2, y2;
int cnt;
int getSize( ){
return ( x2 - x1 +1 ) * ( y2 - y1 + 1 );
}
void print( ){
std::cerr << x1 << " " << y1 << " ; " << x2 << " " << y2 << " - " << cnt << endl;
}
bool check( ){
if( cnt < 0 ) return false;
if( x1 > x2 || y1 > y2 ) return false;
return true;
}
};
const int MAX_N = 128;
bool oke[MAX_N][MAX_N];
void setAll( State curr ){
for( int i=curr.x1 ; i <= curr.x2 ; i++ ){
for( int j=curr.y1 ; j <= curr.y2 ; j++ ){
oke[i][j] = true;
}
}
}
void findTreasure( int n ){
std::queue< State > q;
int total = countTreasure( 1, 1, n, n );
q.push({ 1, 1, n, n, total });
//int cnt = 0;
while( !q.empty() ){ //and cnt++ < 10 ){
State curr = q.front();
q.pop();
curr.print();
if( curr.x1 != curr.x2 and curr.y1 != curr.y2 ){
int xm = ( curr.x1 + curr.x2 ) >> 1;
int ym = ( curr.y1 + curr.y2 ) >> 1;
int A = countTreasure( curr.x1, curr.y1, xm, ym );
int B = countTreasure( curr.x1, curr.y1, xm, curr.y2 );
int C = countTreasure( curr.x1, curr.y1, curr.x2, ym );
cerr << out( A ) << out( B ) << out( C ) << endl;
cerr << out( xm ) << out( ym ) << endl;
cerr << out( curr.cnt ) << " - " << out( ( -A + B + C ) ) << endl;
State a = { curr.x1, curr.y1, xm, ym, A };
State b = { curr.x1, ym+1, xm, curr.y2, B - A }; // top-right quadrant
State c = { xm+1, curr.y1, curr.x2, ym, C - A }; // bottom-left quadrant
State d = { xm+1, ym+1, curr.x2, curr.y2, curr.cnt - ((B - A) + (C - A) + A) };
cerr << " a " << endl;
a.print();
cerr << " b " << endl;
b.print();
cerr << " c " << endl;
c.print();
cerr << " d " << endl;
d.print();
cerr << endl << endl;
if( a.check() and a.cnt ){
if( a.getSize() == a.cnt ) setAll( a );
else q.push( a );
}
if( b.check() and b.cnt ){
if( b.getSize() == b.cnt ) setAll( b );
else q.push( b );
}
if( c.check() and c.cnt ){
if( c.getSize() == c.cnt ) setAll( c );
else q.push( c );
}
if( d.check() and d.cnt ){
if( d.getSize() == d.cnt ) setAll( d );
else q.push( d );
}
}else if( curr.x1 == curr.x2 ){
cerr << " X " << endl;
int ym = ( curr.y1 + curr.y2 ) >> 1;
int A = countTreasure( curr.x1, curr.y1, curr.x1, ym );
cerr << out( curr.x1 ) << out( curr.y1 ) << out( curr.x1 ) << out( ym ) << out( countTreasure( curr.x1, curr.y1, curr.x1, ym ) ) << endl;
cerr << out( A ) << endl;
State a = { curr.x1, curr.y1, curr.x1, ym, A };
State b = { curr.x1, ym+1, curr.x2, curr.y2, curr.cnt - A };
cerr << " a " << endl;
a.print();
cerr << " b " << endl;
b.print();
if( a.check() and a.cnt ){
if( a.getSize() == a.cnt ) setAll( a );
else q.push( a );
}
if( b.check() and b.cnt ){
if( b.getSize() == b.cnt ) setAll( b );
else q.push( b );
}
}else{
cerr << " Y " << endl;
int xm = ( curr.x1 + curr.x2 ) >> 1;
int A = countTreasure( curr.x1, curr.y1, xm, curr.y2);
cerr << out( A ) << endl;
State a = { curr.x1, curr.y1, xm, curr.y2, A };
State b = { xm+1, curr.y1, curr.x2, curr.y2, curr.cnt - A };
if( a.check() and a.cnt ){
if( a.getSize() == a.cnt ) setAll( a );
else q.push( a );
}
if( b.check() and b.cnt ){
if( b.getSize() == b.cnt ) setAll( b );
else q.push( b );
}
}
}
for( int i=1 ; i <= n ; i++ ){
for( int j=1 ; j <= n ; j++ ){
if( oke[i][j] ) Report( i, j );
}
}
}