USACO training chapter1 入门/section1.3
第二部分还是暴力为主。
1.Milking Cows
不是很难,对区间的左端点排序,然后遍历一遍。
可能会有只有一个工人的情况,记得处理。
/*
ID: b1703011
TASK: milk2
LANG: C++
*/
#include <iostream>
#include <algorithm>
using namespace std;
const int max_n = 5010;
struct T
{
int l, r;
bool operator < (const T &t) const {
return l < t.l;
}
} F[max_n];
int main() {
freopen("milk2.in", "r", stdin);
freopen("milk2.out", "w", stdout);
int n;
cin >> n;
for (int i = 0; i < n; i++)
cin >> F[i].l >> F[i].r;
sort(F, F + n);
int res1 = -1, res2 = 0;
int lstr = -1, lstl = -1;
for (int i = 0; i < n; i++) {
if (F[i].l > lstr) {
if (lstr != -1) {
res2 = max(res2, F[i].l - lstr);
}
lstl = F[i].l;
lstr = F[i].r;
res1 = max(res1, F[i].r - F[i].l);
}
else {
lstr = max(lstr, F[i].r);
res1 = max(res1, lstr - lstl);
}
}
cout << res1 << " " << res2 << endl;
return 0;
}
2. Transformations
这个题绝了,神烦。难度不高,就是把一个矩阵的元素分别翻转90度,180度,270度,镜像,然后在镜像后翻转90度,180度,270度。。。。。。。。
写的不是很简洁,没改了。
/*
ID: b1703011
TASK: transform
LANG: C++
*/
#include <iostream>
#include <cstring>
using namespace std;
int n;
char s[12][12], t[12][12], res[12][12];
bool check() {
bool f = true;
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
if(t[i][j] != res[i][j]) {
f = false;
break;
}
}
}
return f;
}
bool rotate_w1() {
//90度旋转
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
t[j][n-1-i] = s[i][j];
}
}
return check();
}
bool rotate_w2() {
//180度旋转
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
t[n-1-i][n-1-j] = s[i][j];
}
}
return check();
}
bool rotate_w3() {
// 270度旋转
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
t[n-1-j][i] = s[i][j];
}
}
return check();
}
bool reflect() {
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
t[i][n-1-j] = s[i][j];
}
}
return check();
}
bool combination() {
for (int i = 0; i < n; i++) {
for (int j = 0; j < n/2; j++) {
int tmp = s[i][n-1-j];
s[i][n-1-j] = s[i][j];
s[i][j] = tmp;
}
}
bool f = false;
if(rotate_w1() || rotate_w2() || rotate_w3()) f = true;
return f;
}
bool NoChange() {
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
t[i][j] = s[i][j];
}
}
return check();
}
int main() {
freopen("transform.in", "r", stdin);
freopen("transform.out", "w", stdout);
cin >> n;
for (int i = 0; i < n; i++) cin >> s[i];
for (int i = 0; i < n; i++) cin >> res[i];
int ans = 7;
if (NoChange()) ans = 6;
if (rotate_w1()) ans = min(ans, 1);
else if (rotate_w2()) ans = min(ans, 2);
else if (rotate_w3()) ans = min(ans, 3);
else if (reflect()) ans = min(ans, 4);
else if (combination()) ans = min(ans, 5);
cout << ans << endl;
return 0;
}
3.Name That Number
这个题两种解法。
第一种是二分查字典,复杂度较高,需要生成一个排列(递归)。
第二种比较巧妙,每个数字对应多个字母,但是每个字母就对应唯一的数字,直接把字典中每个名字转化成数字,然后和输入对比就好了。
/*
ID: b1703011
TASK: namenum
LANG: C++
*/
#include <iostream>
#include <cstring>
#include <algorithm>
#include <cstdio>
using namespace std;
const char num[30] = "22233344455566677778889999";
int main() {
freopen("namenum.in", "r", stdin);
freopen("namenum.out", "w", stdout);
char a[20];
scanf("%s", a);
int m = strlen(a);
bool flag = 0;
freopen("dict.txt", "r", stdin);
char t[20];
while (~scanf("%s", t)) {
int l = strlen(t);
if (l != m) continue;
bool f = 1;
for (int i = 0; i < l; i++) {
if (num[t[i]-'A'] != a[i]) {
f = 0; break;
}
}
if (f == 1) {
printf("%s\n", t);
flag = 1;
}
}
if (flag == 0) printf("NONE\n");
return 0;
}
4.Palindromic Squares
这个题我用的string得到b进制数的字符串
,题目很直接,做法也很直接。
/*
ID: b1703011
TASK: palsquare
LANG: C++
*/
#include <iostream>
#include <algorithm>
#include <cstring>
using namespace std;
const int M = 300;
int B;
string intToA(int a) {
string BNum = "";
while (a > 0) {
int y = a % B;
if (y < 10) BNum += '0' + y;
else BNum += 'A' + y - 10;
a /= B;
}
reverse(BNum.begin(), BNum.end());
return BNum;
}
bool check(int a) {
string BNum = intToA(a);
int cnt = BNum.length();
for (int i = 0; i <= cnt/2; i++) {
if (BNum[i] != BNum[cnt-1-i]) return false;
}
return true;
}
int main() {
freopen("palsquare.in", "r", stdin);
freopen("palsquare.out", "w", stdout);
cin >> B;
string a, b;
for (int i = 1; i <= M; i++) {
if (check(i * i)) {
a = intToA(i);
b = intToA(i * i);
cout << a << " " << b << endl;
}
}
return 0;
}
5. Dual Palindromes
也是很直接。和上题基本一样,换了种写法。
/*
ID: b1703011
TASK: dualpal
LANG: C++
*/
#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
void getNum(int a, int b, char *s) {
int i = 0;
while (a > 0) {
int t = a % b;
if (t < 10) s[i] = t+'0';
else s[i] = t%10+'A';
a /= b;
i++;
}
for (int j = 0; j < i/2; j++) swap(s[j], s[i-j-1]);
s[i] = '\0'; // <-------很重要,不写会出错,不知道为什.
}
bool ispal(char *s, int c) {
for (int i = 0; i < c; i++)
if (s[i] != s[c-i-1]) return false;
return true;
}
int main() {
freopen("dualpal.in", "r", stdin);
freopen("dualpal.out", "w", stdout);
int n, s;
cin >> n >> s;
for (int i = s + 1; n; i++) {
int cnt = 0;
for (int b = 2; b <= 10 && cnt < 2; b++) {
char ss[20];
getNum(i, b, ss);
if (ispal(ss, strlen(ss))) cnt++;
}
if (cnt >= 2) {
cout << i << endl;
n--;
}
}
return 0;
}
预告:下个section是贪心算法(greedy)