QOJ.ac

QOJ

IDProblemSubmitterResultTimeMemoryLanguageFile sizeSubmit timeJudge time
#204035#874. Long Grid CoveringwoshiluoAC ✓660ms4204kbC++206.0kb2023-10-07 00:18:572023-10-07 00:18:57

Judging History

你现在查看的是最新测评结果

  • [2023-10-07 00:18:57]
  • 评测
  • 测评结果:AC
  • 用时:660ms
  • 内存:4204kb
  • [2023-10-07 00:18:57]
  • 提交

answer

/*
 * b.cpp 2023-09-30
 * Copyright (C) 2023 Woshiluo Luo <[email protected]>
 *
 * 「Two roads diverged in a wood,and I—
 * I took the one less traveled by,
 * And that has made all the difference.」
 *
 * Distributed under terms of the GNU GNU AGPLv3+ license.
 */

#include <cstdio>
#include <cstdlib>
#include <cstdint>
#include <cstring>

#include <map>
#include <array>
#include <queue>
#include <vector>
#include <random>
#include <algorithm>

typedef const int cint;
typedef long long ll;
typedef unsigned long long ull;

inline bool isdigit( const char cur ) { return cur >= '0' && cur <= '9'; }/*{{{*/
template <class T> 
T Max( T a, T b ) { return a > b? a: b; }
template <class T> 
T Min( T a, T b ) { return a < b? a: b; }
template <class T> 
void chk_Max( T &a, T b ) { if( b > a ) a = b; }
template <class T> 
void chk_Min( T &a, T b ) { if( b < a ) a = b; }
template <typename T>
T read() { 
	T sum = 0, fl = 1; 
	char ch = getchar();
	for (; isdigit(ch) == 0; ch = getchar())
		if (ch == '-') fl = -1;
	for (; isdigit(ch); ch = getchar()) sum = sum * 10 + ch - '0';
	return sum * fl;
}
template <class T> 
T pow( T a, ll p ) {
	T res = 1;
	while( p ) {
		if( p & 1 ) 
			res = res * a;
		a = a * a;
		p >>= 1;
	}
	return res;
}/*}}}*/

const int mod = 1e9 + 7;

struct ModInt {/*{{{*/
	int32_t cur;
	ModInt( const int64_t _cur = 0 ) { cur = ( ( ( _cur % mod ) + mod ) % mod ); }

	inline ModInt operator+ ( const ModInt &b ) const { return ( cur + b.cur ) % mod; }
	inline ModInt operator- ( const ModInt &b ) const { return ( ( ( cur - b.cur ) % mod ) + mod ) % mod; }
	inline ModInt operator* ( const ModInt &b ) const { return ( 1LL * cur * b.cur ) % mod; }
	inline ModInt operator/ ( const ModInt &b ) const { return ( 1LL * cur * pow( b, mod - 2 ).cur ) % mod; }

	inline void operator+= ( const ModInt &b ) { (*this) = (*this) + b; }
	inline void operator-= ( const ModInt &b ) { (*this) = (*this) - b; }
	inline void operator*= ( const ModInt &b ) { (*this) = (*this) * b; }
	inline void operator/= ( const ModInt &b ) { (*this) = (*this) / b; }

	inline void output( const char end = '\n' ) { printf( "%d%c", cur, end ); }
};/*}}}*/

const int32_t P = 1 << 9;

int32_t hash( const int32_t x, const int32_t y ) {
	return ( 2 - y ) * 3 + x;
}
uint32_t full_pow( const uint32_t cur ) {
	return 1 << cur;
}
uint32_t set_bit( const uint32_t cur, const uint32_t pos ) {
	return cur | full_pow(pos);
}
bool chk_pos( const uint32_t cur, const uint32_t pos ) {
	return ( cur >> pos ) & 1;
}

ModInt f[P], orip[P][P];

const int LP = 24;
struct Matrix {/*{{{*/
	ModInt a[LP][LP];
	Matrix( const int cur = 0 ) {
		if( cur ) 
			for( int i = 0; i < LP; i ++ ) 
				a[i][i] = 1;
	}
	Matrix operator* ( const Matrix &_b ) const {
		Matrix res;
		for( int i = 0; i < LP; i ++ ) {
			for( int j = 0; j < LP; j ++ ) {
				for( int k = 0; k < LP; k ++ ) {
					res.a[i][j] += a[i][k] * _b.a[k][j];
				}
			}
		}
		return res;
	}
	void operator*= ( const Matrix &_b ) { (*this) = (*this) * _b; }
} p;/*}}}*/

struct Node { int32_t x, y; };
Node block[][3] = { 
	{ { 0, 0 }, { 0, 1 }, { 0, 2 } },
	{ { 0, 0 }, { 1, 0 }, { 2, 0 } },
	{ { 0, 0 }, { 0, 1 }, { 1, 0 } },
	{ { 0, 0 }, { 0, 1 }, { 1, 1 } },
	{ { 0, 0 }, { 1, 0 }, { 1, 1 } },
	{ { 0, 1 }, { 1, 0 }, { 1, 1 } },
};

int main() {
#ifdef woshiluo
	freopen( "l.in", "r", stdin );
	freopen( "l.out", "w", stdout );
#endif
	std::vector<uint32_t> blocks;
	{/*{{{*/
		auto chk = [] ( const int32_t cur, const int32_t left, const int32_t rig ) { return ( cur >= left ) && ( cur < rig ); };
		for( int o = 0; o < 6; o ++ ) {
			const auto v = block[o];
			for( int i = 0; i < 3; i ++ ) {
				int mask = 0;
				bool flag = true;
				for( int k = 0; k < 3; k ++ ) {
					const auto node = v[k];
					if( chk( node.x + i, 0, 3 ) ) {
						mask = set_bit( mask, hash( node.x + i, node.y ) );
						continue;
					}
					flag = false;
					break;
				}
				if( !flag ) 
					continue;
				blocks.push_back(mask);
			}
		}
	}/*}}}*/

	for( uint32_t sta = 0; sta < full_pow(12); sta ++ ) {/*{{{*/
		bool flag = true;
		int mask = 0;
		for( int j = 0; j < 12; j ++ ) {
			if( chk_pos( sta, j ) == false )
				continue;
			if( mask & blocks[j] ) 
				flag = false;
			mask |= blocks[j];
		}
		if( flag )
			f[mask] += 1;
	}
	/*}}}*/


	for( uint32_t i = 0; i < full_pow(6); i ++ ) {
		for( uint32_t j = 0; j < full_pow(6); j ++ ) {
			if( ( ( j >> 3 ) & 7 ) < ( i & 7 ) )
				continue;
			const int32_t mask = ( ( 7 ^ ( ( i >> 3 ) & 7 ) ) << 6 ) |
				( ( ( ( j >> 3 ) & 7 ) ^ ( i & 7 ) ) << 3 ) |
				( ( j & 7 ) );
			orip[i][j] += f[mask];
		}
	}

	std::vector<int> nums;
	for( uint32_t i = 0; i < full_pow(6); i ++ ) {
		for( uint32_t j = 0; j < full_pow(6); j ++ ) {
			if( orip[i][j].cur ) {
				if( i != 0 && j != 0 && ( i <= 7 || std::__popcount(i) < 3 || std::__popcount(j) < 3 ) ) {
					orip[i][j] = 0;
				}
				else {
					nums.push_back( i );
					nums.push_back( j );
#ifdef woshiluo
					printf( "(%d,%d) = %3d\n", i, j, orip[i][j].cur );
#endif
				}
			}
		}
	}

	std::sort( nums.begin(), nums.end() );
	nums.erase( std::unique( nums.begin(), nums.end() ), nums.end() );
	auto find = [&nums]( const int32_t cur ) { return std::lower_bound( nums.begin(), nums.end(), cur ) - nums.begin(); };
	for( uint32_t i = 0; i < full_pow(6); i ++ ) {
		for( uint32_t j = 0; j < full_pow(6); j ++ ) {
			if( orip[i][j].cur ) {
				p.a[ find(i) ][ find(j) ] = orip[i][j];
			}
		}
	}

	int T = read<int>();
	std::vector<std::pair<ll, int>> q;
	std::vector<ModInt> ans(T);
	for( int i = 0; i < T; i ++ ) {
		q.push_back( { read<ll>(), i } );
	}
	std::sort( q.begin(), q.end() );
	Matrix a;
	a.a[0][0] = 1;
	ll la = 0;
	for( auto &pair: q ) {
		const auto diff = pair.first - la;
		la = pair.first;
		if( diff != 0 )
			a = a * pow( p, diff );
		ans[ pair.second ] = a.a[0][0];
	}
	for( auto &x: ans ) 
		x.output();
}

Details

Tip: Click on the bar to expand more detailed information

Test #1:

score: 100
Accepted
time: 2ms
memory: 4204kb

input:

4
1
2
3
10

output:

1
3
10
8266

result:

ok 4 number(s): "1 3 10 8266"

Test #2:

score: 0
Accepted
time: 48ms
memory: 4056kb

input:

100
591
417
888
251
792
847
685
3
182
461
102
348
555
956
771
901
712
878
580
631
342
333
285
899
525
725
537
718
929
653
84
788
104
355
624
803
253
853
201
995
536
184
65
205
540
652
549
777
248
405
677
950
431
580
600
846
328
429
134
983
526
103
500
963
400
23
276
704
570
757
410
658
507
620
984
2...

output:

398162564
3923746
347206084
937652677
511984221
356815867
634269583
10
492672877
107350060
647965529
633393631
911425824
746373395
426043114
551287175
772111460
994877654
877599230
88346652
250024200
154039310
461178023
487763582
763918729
537233428
570954868
210301204
911464697
237056565
669291182
...

result:

ok 100 numbers

Test #3:

score: 0
Accepted
time: 660ms
memory: 3980kb

input:

100
955967370573984956
113166936398978672
934415284373637608
774686535590919223
668528836699949629
65629257521619533
811940940990692618
915621972787306932
228144645291423602
690041707309747302
191003462832708740
981404451712468361
900400340973685384
507894895830950112
730342794302458267
292630995901...

output:

544144276
818067446
86599466
313726969
18938569
632700031
797497759
781547720
391588017
878181169
310434443
416689342
69020235
460227545
162825045
321960509
604698726
745824316
617383608
26101176
816251396
489328969
613075753
821553025
821486393
270559043
786443427
729545800
129844182
893901263
9674...

result:

ok 100 numbers

Test #4:

score: 0
Accepted
time: 30ms
memory: 4052kb

input:

100
1000000000000000000
999999999999999999
999999999999999998
999999999999999997
999999999999999996
999999999999999995
999999999999999994
999999999999999993
999999999999999992
999999999999999991
999999999999999990
999999999999999989
999999999999999988
999999999999999987
999999999999999986
9999999999...

output:

776755633
305596516
433884536
271324944
255217955
752347893
279777560
954593517
141741201
121847646
925987319
408911539
615371540
395678394
900921829
709870350
988659472
113218064
830032042
970158982
295607870
455576442
901184396
886355576
365985700
530063682
646456471
944296960
543981115
362793239
...

result:

ok 100 numbers