海亮 7.22 周赛
海亮 7.22 周赛
\(T2\)忘判断右上方扩展的情况 导致挂了二十分钟 凸(艹皿艹 )
\(T4\)死活没想到是\(9\)的倍数 急 暴搜不懂为啥挂了
不过\(T3\)一眼秒了 也算是进步罢
#A. 签到题
#include <bits/stdc++.h>
using namespace std;
#define endl '\n'
int read ()
{
int x = 0 , f = 1;
char ch = cin.get();
while ( !isdigit ( ch ) ) { if ( ch == '-' ) f = -1; ch = cin.get(); }
while ( isdigit ( ch ) ) { x = ( x << 1 ) + ( x << 3 ) + ( ch ^ 48 ); ch = cin.get(); }
return x * f;
}
signed main ()
{
ios::sync_with_stdio(false);
cin.tie(0) , cout.tie(0);
int T = read();
switch (T)
{
case 1: { cout << 4 << endl; break; }
case 2: { cout << 9 << endl; break; }
case 3: { cout << 6 << endl; break; }
case 4: { cout << 7 << endl; break; }
case 5: { cout << "DeaphetS" << endl; break; }
}
return 0;
}
#B. 五子棋(five)
模拟即可 因为没判断右上方五个棋子的情况挂了二十分钟
#include <bits/stdc++.h>
using namespace std;
#define endl '\n'
constexpr int N = 40 + 5;
const int dx[4] = { 1 , 0 , 1 , 1 };
const int dy[4] = { 0 , 1 , 1 , -1 };
int read ()
{
int x = 0 , f = 1;
char ch = cin.get();
while ( !isdigit ( ch ) ) { if ( ch == '-' ) f = -1; ch = cin.get(); }
while ( isdigit ( ch ) ) { x = ( x << 1 ) + ( x << 3 ) + ( ch ^ 48 ); ch = cin.get(); }
return x * f;
}
int n , f[N][N];
int check ()
{
for ( int i = 1 ; i <= 15 ; i ++ )
for ( int j = 1 ; j <= 15 ; j ++ )
{
for ( int k = 0 ; k < 4 ; k ++ )
{
int col = f[i][j];
if ( f[i][j] == -1 ) continue;
int pd = 1 , tx = i, ty = j;
for ( int l = 2 ; l <= 5 ; l ++ )
{
tx = tx + dx[k] , ty = ty + dy[k];
if ( f[tx][ty] != col || ( ! ( 1 <= tx && tx <= 15 && 1 <= ty && ty <= 15 ) ) ) { pd = 0; break; }
}
if ( pd == 1 ) return f[i][j];
}
}
return -1;
}
signed main ()
{
// freopen ( "ex_five1.in" , "r" , stdin );
ios::sync_with_stdio(false);
cin.tie(0) , cout.tie(0);
memset ( f , -1 , sizeof f );
n = read();
for ( int i = 1 ; i <= n ; i ++ )
{
int u = read() , v = read();
f[u][v] = ( i % 2 );
if ( check() != -1 ) { cout << ( ( check() == 1 ) ? "A" : "B" ) << ' ' << i << endl; return 0; }
}
cout << "Tie" << endl;
return 0;
}
#C. 加边
一眼秒了 没看到\(2000\)的数据范围 上去打了\(floyd\)然后\(T\)了 才看数据范围()
\(dijkstra\)即可
正确性来自统计原图两点之间的最短路之后 如果在这两个点之间加边 只会影响这一条最短路和\(1\)的大小关系
#include <bits/stdc++.h>
using namespace std;
#define endl '\n'
#define pb push_back
constexpr int N = 2000 + 5;
const int dx[4] = { 1 , 0 , 1 , 1 };
const int dy[4] = { 0 , 1 , 1 , -1 };
int read ()
{
int x = 0 , f = 1;
char ch = cin.get();
while ( !isdigit ( ch ) ) { if ( ch == '-' ) f = -1; ch = cin.get(); }
while ( isdigit ( ch ) ) { x = ( x << 1 ) + ( x << 3 ) + ( ch ^ 48 ); ch = cin.get(); }
return x * f;
}
int n , m , dis[N][N] , ans;
vector<int> e[N];
struct DQY
{
int dis , id;
friend bool operator < ( const DQY &a , const DQY &b ) { return a.dis > b.dis; };
};
priority_queue<DQY> q;
void dij ( int s )
{
dis[s][s] = 0;
q.push ( { dis[s][s] , s } );
while ( !q.empty() )
{
int u = q.top().id , ff = q.top().dis;
q.pop();
if ( ff != dis[s][u] ) continue;
for ( auto v : e[u] )
if ( dis[s][v] > dis[s][u] + 1 )
{
dis[s][v] = dis[s][u] + 1;
q.push ( { dis[s][v] , v } );
}
}
}
signed main ()
{
ios::sync_with_stdio(false);
cin.tie(0) , cout.tie(0);
n = read() , m = read();
if ( m == 0 ) { cout << 0 << endl; return 0; }
memset ( dis , 0x3f3f3f3f , sizeof dis );
for ( int i = 1 , u , v ; i <= m ; i ++ )
u = read() , v = read() , e[u].pb(v);
for ( int i = 1 ; i <= n ; i ++ ) dij(i);
for ( int i = 1 ; i <= n ; i ++ )
for ( int j = 1 ; j <= n ; j ++ )
{
if ( i == j ) continue;
ans += ( dis[i][j] > 1 && dis[i][j] != 0x3f3f3f3f );
}
cout << ans << endl;
return 0;
}
#D. 絶対、大丈夫!(yukikaze)
小学奥数 我们可以知道\(10k\)和\(k\)的数字组成是相同的
那么我们将原来的\(p\)串构造成\(9\)的倍数即可
那么我们钦定它加在最后一位 再高精度除以\(9\)即可
#include <bits/stdc++.h>
using namespace std;
#define endl '\n'
constexpr int N = 5e5 + 5;
int read ()
{
int x = 0 , f = 1;
char ch = cin.get();
while ( !isdigit ( ch ) ) { if ( ch == '-' ) f = -1; ch = cin.get(); }
while ( isdigit ( ch ) ) { x = ( x << 1 ) + ( x << 3 ) + ( ch ^ 48 ); ch = cin.get(); }
return x * f;
}
int n , sum , a[N] , res[N];
string ss;
signed main ()
{
ios::sync_with_stdio(false);
cin.tie(0) , cout.tie(0);
cin >> ss;
for ( int i = 0 ; i < ss.size() ; i ++ ) a[i+1] = ss[i] - '0';
n = ss.size() + 1;
for ( int i = 1 ; i <= n ; i ++ ) sum += a[i];
int add = 9 - ( sum % 9 );
cout << add << endl;
a[n] = add;
for ( int i = 1 ; i <= n ; i ++ ) res[i] = a[i] / 9 , a[i+1] += ( a[i] % 9 ) * 10;
for ( int i = 1 ; i <= n + 1 ; i ++ ) cout << res[i];
cout << endl;
for ( int i = 0 ; i <= n ; i ++ ) cout << res[i];
return 0;
}
#E. matrix
一眼状态压缩 用记忆化书写()
注意边界的判断(在边界的时候不能使用+1或-1状态)
状压题解真写不出来什么 还是多做题罢
#include <bits/stdc++.h>
using namespace std;
#define endl '\n'
#define int long long
constexpr int N = 10 + 5;
constexpr int M = 1024 + 5;
constexpr int inf = 0x3f3f3f3f3f3f3f3f;
#define getchar() cin.get()
int read ()
{
int x = 0 , f = 1;
char ch = getchar();
while ( !isdigit ( ch ) ) { if ( ch == '-' ) f = -1; ch = getchar(); }
while ( isdigit ( ch ) ) { x = ( x << 1 ) + ( x << 3 ) + ( ch ^ 48 ); ch = getchar(); }
return x * f;
}
int a[N][N] , mp[N][N] , f[N][M][M] , st[N] , n , m;
int dfs ( int row , int now , int lst )
{
// cout << row << ' ' << now << ' ' << lst << endl;
if ( f[row][now][lst] != inf ) return f[row][now][lst];
for ( int i = 0 ; i < ( 1 << m ) ; i ++ )//枚举这一层的按灯状态
if ( row == 1 || ( i | lst ) == ( 1 << m ) - 1 )
{
int res = 0 , temp = now;
for ( int j = 1 ; j <= m ; j ++ )
if ( i & ( 1 << j - 1 ) )
{
res += a[row][j] , temp |= ( 1 << j - 1 );
if ( j != 1 ) temp |= ( 1 << j - 2 );
if ( j != m ) temp |= ( 1 << j );
}
if ( row == n )
{
if ( temp == ( 1 << m ) - 1 )
f[row][now][lst] = min ( f[row][now][lst] , res );
}
else f[row][now][lst] = min ( f[row][now][lst] , dfs ( row + 1 , st[row+1] | i , temp ) + res );
}
return f[row][now][lst];
}
char ch;
signed main ()
{
ios::sync_with_stdio(false);
cin.tie(0) , cout.tie(0);
// freopen ( "a.in" , "r" , stdin );
memset ( f , inf , sizeof f );
n = read() , m = read();
for ( int i = 1 ; i <= n ; i ++ )
for ( int j = 1 ; j <= m ; j ++ )
cin >> ch , mp[i][j] = ch - '0';
// for ( int i = 1 ; i <= n ; i ++ , cout.put(endl) )
// for ( int j = 1 ; j <= m ; j ++ )
// cout << mp[i][j] << ' ';
for ( int i = 1 ; i <= n ; i ++ )
for ( int j = 1 ; j <= m ; j ++ )
if ( mp[i][j] )
st[i] |= ( 1 << ( j - 1 ) );
for ( int i = 1 ; i <= n ; i ++ )
for ( int j = 1 ; j <= m ; j ++ )
a[i][j] = read();
cout << dfs ( 1 , st[1] , 0 ) << endl;
return 0;
}