C,D虽然思路很容易,但是代码实现要一点细节。其余都很简单。
A. Space Navigation
题目链接:点击此处
因为可以随意删除,所以只要知道单独上下左右最远到哪就行。
#include<iostream>
#include<vector>
#include<cstring>
#include<algorithm>
#include<cmath>
#include<iomanip>
#include<stdio.h>
#include<map>
#include<queue>
using namespace std;
typedef long long ll;
const int MAXN = 3e5 + 5;
const int MAXM = 1e6 + 5;
const ll mod = 1e9 + 7;
ll n, m,cnt;
int main() {
int t;
cin >> t;
while (t--) {
int a = 0, b = 0, c = 0, d = 0;
int x, y;
cin >> x >> y;
string str;
cin >> str;
int len = str.length();
for (int i = 0;i < len;i++) {
if (str[i] == 'U')a++;
if (str[i] == 'D')b--;
if (str[i] == 'R')c++;
if (str[i] == 'L')d--;
}
if (x <= c && x >= d && y <= a && y >= b)cout << "YES" << endl;
else cout << "NO" << endl;
}
}
B. New Colony
题目链接:点击此处
数据量小,可以考虑直接暴力,然后想到k如果很大会不会爆掉,答案不会,因为100*100最多10000,所以k最多只要10000,就可以填满坑。所以最多k循环1e4次,复杂度很小,我们后面就直接暴力枚举看石头滚到哪就行,复杂度1e6。
#include<iostream>
#include<vector>
#include<string>
#include<algorithm>
#include<cmath>
#include<iomanip>
#include<stdio.h>
#include<map>
#include<queue>
using namespace std;
typedef long long ll;
const int MAXN = 3e5 + 5;
const int MAXM = 1e6 + 5;
const ll mod = 1e9 + 7;
ll n, m,cnt;
ll arr[MAXN];
int main() {
int t;
cin >> t;
while (t--) {
cin >> n >> m;
for (int i = 1;i <= n;i++) {
cin >> arr[i];
}
bool f = false;
int pre = -1;
for (int i = 1;i <= m;i++) {
bool ff = false;
for (int j = 1;j <= n-1;j++) {
if (arr[j] < arr[j + 1]) {
ff = true;
pre = j;
arr[j]++;break;
}
}
if (!ff) { f = true; break; }
}
if (f)cout << -1 << endl;
else cout << pre << endl;
}
}
C. Fence Painting
题目链接:点击此处
因为对于 c c c而言,从左往右开始。所以对于最后一个 c [ m ] c[m] c[m],如果他涂的颜色在 b b b中没有,那么必定不成功,如果有,那么对于所有 c c c而言,一旦需要涂一个不需要的颜色后,就涂颜色 c [ m ] c[m] c[m]的那一块,最后用 c [ m ] c[m] c[m]覆盖就行。
思路很简单。代码实现要点细节,我用队列表示要涂的位置,然后在 a [ i ] ! = b [ i ] a[i]!=b[i] a[i]!=b[i]的时候更新 p o s pos pos值,主要目的时要知道最后涂的 c [ m ] c[m] c[m]的确切的位置。即确保 i n t p = p o s [ c [ m ] ] ; int~p = pos[c[m]]; int p=pos[c[m]];这行代码正确。
#include<iostream>
#include<vector>
#include<string>
#include<algorithm>
#include<cmath>
#include<iomanip>
#include<stdio.h>
#include<map>
#include<queue>
using namespace std;
typedef long long ll;
const int MAXN = 3e5 + 5;
const int MAXM = 1e6 + 5;
const ll mod = 1e9 + 7;
ll n, m,cnt;
ll a[MAXN],b[MAXN],c[MAXN];
ll tong[MAXN];
ll ans[MAXN];
bool visit[MAXN];
queue<int>q[MAXN];
int pos[MAXN];
int main() {
int t;
cin >> t;
while (t--) {
cin >> n >> m;
for (int i = 1;i <= n;i++) cin >> a[i];
for (int i = 1;i <= n;i++) {
cin >> b[i];
visit[b[i]] = 1;
pos[b[i]] = i;
}
for (int i = 1;i <= m;i++) cin >> c[i];
for (int i = 1;i <= n;i++) {
if (a[i] != b[i]) { tong[b[i]]++; q[b[i]].push(i);pos[b[i]] = i; }
a[i] = b[i] = 0;
}
bool f = true;
if (visit[c[m]] == false) {
f = false;
}
int p = pos[c[m]];
for (int i = 1;i <= m;i++) {
if (tong[c[i]] > 0) {
tong[c[i]]--;
int now = q[c[i]].front();
q[c[i]].pop();
ans[i] = now;
}
else ans[i] = p;
}
for (int i = 1;i <= n;i++) {
if (tong[i] != 0)f = false;
visit[i] = 0;
pos[i] = 0;
tong[i] = 0;
while (!q[i].empty())q[i].pop();
}
if (!f) {
cout << "NO" << endl;continue;
}
cout << "YES" << endl;
for (int i = 1;i <= m;i++) { cout << ans[i] << " "; }
cout << endl;
}
}
D. AB Graph
题目链接:点击此处
虽然代码长,但是感觉比C题简单。很容易想到。
首先一旦两点之间两条边相同字母,就可以满足任意m。
如果不存在的话,那么我们要考虑n=2和n>2,原因时n>=3时必定使得3个点中出现一种情况,这种情乱搞满足任何m。
n=2时,并且两条边不同,对于偶数就输出NO,对于奇数换来换去就行。
n>2时,我们先找出点1,2,3中哪个点满足特殊情况。
假设给出
n=3
*ab
b*b
aa*
自己画一下。
这个图满足任意两点之间的两边的字母都不同。
但是我对于m为奇数,循环走就行。
m%4=0时,我们走1->2->1->3->1的路线
m%4=2时,我们走3->1->2->1->3->1->2路线。
举例,m=8,我们走1->2->1->3 -> 1->2->1->3->1
m=10,我们走3->1->2->1->3 -> 1->2->1->3->1->2
很容易发现规律,后续只要代码模拟就行。
#include<iostream>
#include<vector>
#include<string>
#include<algorithm>
#include<cmath>
#include<iomanip>
#include<stdio.h>
#include<map>
#include<queue>
using namespace std;
typedef long long ll;
const int MAXN = 1e3 + 5;
const int MAXM = 1e6 + 5;
const ll mod = 1e9 + 7;
ll n, m,cnt;
char mp[MAXN][MAXN];
void yes() { cout << "YES" << endl; }
int main() {
int t;
cin >> t;
while (t--) {
cin >> n >> m;
for (int i = 1;i <= n;i++) {
for (int j = 1;j <= n;j++) {
cin >> mp[i][j];
}
}
bool f = false;
int x, y;
for (int i = 1;i <= n;i++) {
for (int j = i+1;j <= n;j++) {
if (mp[i][j] == mp[j][i]) {
f = true;
x = i;
y = j;
break;
}
}
}
if (f) {
yes();
for (int i = 1;i <= m+1;i++) {
cout << ((i % 2 == 0) ? x : y) << " ";
}
cout << endl;
continue;
}
int a, b, c;
if (n == 2) {
if (mp[1][2] != mp[2][1] && m % 2 == 0) {
cout << "NO" << endl;
}
else {
yes();
x = 1, y = 2;
for (int i = 1;i <= m+1;i++) {
cout << ((i % 2 == 0) ? x : y) << " ";
}
cout << endl;
}
continue;
}
if (mp[1][2] == mp[3][1]) { a = 1, b = 2, c = 3; }
else if (mp[2][3] == mp[1][2]) { a = 2, b = 3, c = 1; }
else {
a = 3, b = 1, c = 2;
}
if (m % 2 == 1) {
yes();
for (int i = 1;i <= m+1;i++) {
cout << (i % 2 == 0 ? a : b) << " ";
}
cout << endl;
}
else if (m % 4 == 0) {
yes();
for (int i = 1;i <= m;i+=4) {
cout << a << " " << b << " "<< a << " " << c << " ";
}
cout << a << endl;
}
else {
yes();
cout << c << " ";
for (int i = 1;i <= m-2;i+=4) {
cout << a << " " << b << " " << a << " " << c << " ";
}
cout << a << " ";
cout << b << " ";
cout << endl;
}
}
}