C - Same Map in the RPG World
问题描述
高桥正在开发一个RPG游戏。他决定编写一段代码来检查两个地图是否相等。
我们有一个 AA 和一个 BB,它们分别有 HH 行和 WW 列。每个单元格上都写着符号 #
或 .
。
在 AA 和 BB 中,位于从上往下数第 ii 行和从左往右数第 jj 列的单元格上的符号分别用 Ai,jAi,j 和 Bi,jBi,j 表示。
以下两种操作分别称为 垂直移动 和 水平移动。
- 对于每个 j=1,2,…,Wj=1,2,…,W,同时执行以下操作:
- 同时用 A2,j,A3,j,…,AH,j,A1,jA2,j,A3,j,…,AH,j,A1,j 替换 A1,j,A2,j,…,AH−1,j,AH,jA1,j,A2,j,…,AH−1,j,AH,j。
- 对于每个 i=1,2,…,Hi=1,2,…,H,同时执行以下操作:
- 同时用 Ai,2,Ai,3,…,Ai,W,Ai,1Ai,2,Ai,3,…,Ai,W,Ai,1 替换 Ai,1,Ai,2,…,Ai,W−1,Ai,WAi,1,Ai,2,…,Ai,W−1,Ai,W。
是否存在一对非负整数 (s,t)(s,t) 满足以下条件?如果存在,则打印 Yes
,否则打印 No
。
- 经过 ss 次垂直移动和 tt 次水平移动后,AA 等于 BB。
这里,当且仅当对于所有整数对 (i,j)(i,j) 满足 Ai,j=Bi,jAi,j=Bi,j 时,AA 被称为等于 BB。
约束条件
- 2≤H,W≤302≤H,W≤30
- Ai,jAi,j 为
#
或.
,Bi,jBi,j 也是如此。 - HH 和 WW 为整数。
输入
输入以以下格式从标准输入给出:
HH WW A1,1A1,2…A1,WA1,1A1,2…A1,W A2,1A2,2…A2,WA2,1A2,2…A2,W ⋮⋮ AH,1AH,2…AH,WAH,1AH,2…AH,W B1,1B1,2…B1,WB1,1B1,2…B1,W B2,1B2,2…B2,WB2,1B2,2…B2,W ⋮⋮ BH,1BH,2…BH,WBH,1BH,2…BH,W
输出
如果存在符合条件的整数对 (s,t)(s,t),则打印
Yes
;否则打印No
。
样例1
Inputcopy | Outputcopy |
---|---|
4 3 ..# ... .#. ... #.. ... .#. ... |
Yes |
通过选择 (s,t)=(2,1)(s,t)=(2,1),得到的 AA 等于 BB。
当选择 (s,t)=(2,1)(s,t)=(2,1) 时,我们描述了具体的过程。最初,AA 如下所示。
..# ... .#. ...
我们首先进行垂直移动,使得 AA 如下所示。
... .#. ... ..#
然后我们再进行一次垂直移动,使得 AA 如下所示。
.#. ... ..# ...
最后,我们进行一次水平移动,使得 AA 如下所示,它等于 BB。
#.. ... .#. ...
样例2
Inputcopy | Outputcopy |
---|---|
3 2 ## ## #. .. #. #. |
No |
没有选择 (s,t)(s,t) 使得 AA 等于 BB。
样例3
Inputcopy | Outputcopy |
---|---|
4 5 ##### .#... .##.. ..##. ...## #...# ##### ...#. |
Yes |
样例4
Inputcopy | Outputcopy |
---|---|
10 30 ..........##########.......... ..........####....###.....##.. .....##....##......##...#####. ....####...##..#####...##...## ...##..##..##......##..##....# #.##....##....##...##..##..... ..##....##.##..#####...##...## ..###..###..............##.##. .#..####..#..............###.. #..........##................. ................#..........##. ######....................#### ....###.....##............#### .....##...#####......##....##. .#####...##...##....####...##. .....##..##....#...##..##..##. ##...##..##.....#.##....##.... .#####...##...##..##....##.##. ..........##.##...###..###.... ...........###...#..####..#... |
Yes |
#include <iostream>
#include <vector>
using namespace std;
bool isEqual(vector<vector<char>>&A, vector<vector<char>>&B, int H, int W, int s, int t)
{
for (int i = 0; i < H; i++) {
for (int j = 0; j < W; j++) {
int new_i = (i + s) % H;
int new_j = (j + t) % W;
if (A[i][j] != B[new_i][new_j]) {
return false;
}
}
}
return true;
}
int main()
{
int H, W;
cin >> H >> W;
vector<vector<char>>A(H, vector<char>(W));
vector<vector<char>>B(H, vector<char>(W));
for (int i = 0; i < H; i++) {
for (int j = 0; j < W; j++) {
cin >> A[i][j];
}
}
for (int i = 0; i < H; i++) {
for (int j = 0; j < W; j++) {
cin >> B[i][j];
}
}
for (int s = 0; s < H; s++) {
for (int t = 0; t < W; t++) {
if (isEqual(A, B, H, W, s, t)) {
cout << "Yes" << endl;
return 0;
}
}
}
cout << "No" << endl;
return 0;
}
注意点:
这种需要重复变换矩阵元素的一般情况下都是需要取模的,而不需要一直变换矩阵
D - Base 2
#include <iostream>
#include <algorithm>
#include <math.h>
using namespace std;
int main()
{
unsigned long long sum = 0;
for (int i = 0; i < 64; i++) {
int a;
cin >> a;
if(a)sum += (1LL<<i);
}
cout << sum << endl;
return 0;
}
注意点:
整形溢出,要用unsigned long long,不要用long long,这样会有负数溢出,把这个忘了(Oh my god)
E - Friends and Travel costs
#include <iostream>
#include <algorithm>
using namespace std;
long long res ;
struct f
{
long long num;
long long money;
}a[200005];
bool cmp(f a, f b) {
return a.num < b.num;
}
int main()
{
long long n, k;
cin >> n >> k;
for (int i = 0; i < n; i++) {
cin >> a[i].num >> a[i].money;
}
sort(a, a + n, cmp);
long long cur_v = 0;
long long cur_m = k;
for (int i = 0; i < n; i++) {
long long distance = a[i].num - cur_v;
if (cur_m >= distance) {
cur_v = a[i].num;
cur_m -= distance;
cur_m += a[i].money;
}
else {
break;
}
}
if (cur_m)cur_v += cur_m;
cout << cur_v << endl;
return 0;
}
注意点:
1,需要对朋友所在的村庄进行排序
2,每到一个地方,都要扣1日元
F - Centers
#include <iostream>
#include <algorithm>
using namespace std;
typedef long long ll;
ll temp[200005] = { 0 };
struct f {
ll index;
ll value;
}counter[200005];
bool cmp(f a, f b) {
return a.index < b.index;
}
int main()
{
ll n;
cin >> n;
for (int i = 1; i <= 3 * n; i++) {
ll x;
cin >> x;
temp[x]++;
if (temp[x] == 2) {
counter[x].index = i;
counter[x].value = x;
}
}
sort(counter + 1, counter + 1 + n, cmp);
for (int i = 1; i <= n; i++)
cout << counter[i].value << " ";
return 0;
}
注意点:
1,在for循环输入的时候,当temp[x]==2时,要保存的是counter[x]的数据,而不是counter[i]的数据,原因:自己在草稿纸上验算一下输出的结果就能发现
G - AABCC
#include <iostream>
using namespace std;
typedef long long ll;
bool f[10000005];//标记是否为素数
ll prime[200005];//存储素数
void counter()
{
for (ll i = 2; i < 1000005; i++) {
if (!f[i]) {
f[i] = 1;
for (ll j = i + i; j <= 1000005; j += i) {
f[j] = 1;
}
prime[++prime[0]] = i;
}
}
ll n;
int count = 0;
cin >> n;
for (int i = 1; i <= prime[0]; i++) {
if (prime[i] * prime[i] * prime[i] * prime[i] * prime[i] > n) {
break;
}
for (int j = i + 1; j <= prime[0]; j++) {
if (prime[i] * prime[i] * prime[j] * prime[j] * prime[j]>n) {
break;
}
for (int k = j + 1; k <= prime[0]; k++) {
if (prime[i] * prime[i] * prime[j] * prime[k] * prime[k] <= n)count++;
else break;
}
}
}
cout << count << endl;
}
int main()
{
counter();
return 0;
}
注意点:
1,prime[0]其实就是素数的个数,每次都会自我更新
2,新的标记素数的算法:埃拉托斯特尼筛法