关于练习赛:
这次练习赛出的比较基础,比较难一点的就是L-U但是也不是很难就是简单的模拟和排序,基本就是L1 10-20分难度左右,所以题解也是出L-U的题解.
L题:
算的时候先算俩圈总共720然后顺时针或者逆时针找最小度数到第一个数,然后逆时针转,如果能找到第二或者第三个数就+360不能的在多转度数。
# include <iostream>
# include <cstdio>
using namespace std;
const double pi = 3.1415926;
using namespace std;
const int N = 40;
int main()
{
int n, num1, num2, num3;
while(cin >> n >> num1 >> num2 >> num3 , (n || num1 || num2 || num3))
{
int du = 0;
du += (N + N);
int t1 = n - num1 >= 0 ? n - num1 : n - num1 + N;
int t2 = num1 - n >= 0 ? num1 - n : num1 - n + N;
du += min(t1, t2);
du += N;
du += num2 - num1 > 0 ? num2 - num1 : num2 - num1 + N;
du += num2 - num3 > 0 ? num2 - num3 : num2 - num3 + N;
cout << du * 9 << endl;
}
return 0;
}
M题:
M题就是一个简单的找数问题,找一个区间里的最中间的数,不停的更新下上限和下限就好。
# include <iostream>
# include <cstdio>
# include <string>
using namespace std;
int main(int argc, char *argv[])
{
string str;
int n;
int minn = 0, maxx = 10005;
while(cin >> n)
{
getchar();
getline(cin, str);
// cout << str << endl;
if(str == "too high")
{
if(maxx > n)
maxx = n;
}
else if(str == "too low")
{
if(minn < n)
minn = n;
}
else if(str == "right on")
{
if( n < maxx && n > minn)
{
cout << "Xiaoz may be honest" << endl;
}
else
{
cout << "Xiaoz is dishonest" << endl;
}
minn = 0, maxx = 10005;
}
}
return 0;
}
N题:
找到公共质因数找倍数取反就可以,先打一个素数表,然后依次把倍数取反。
# include <iostream>
# include <cmath>
# include <vector>
# include <cstring>
using namespace std;
const int maxn = 1000005;
bool arr[maxn];
int num[maxn];
bool flag[maxn];
int s = 0;
//ÏßÐÔɸѡ·¨
void fun()
{
s = 0;
arr[0] = arr[1] = 1;
for(int i = 2; i < maxn; i++)
{
if(!arr[i])
{
num[s++] = i;
}
for(int j = 0; j < s && num[j] * i < maxn; j++)
{
arr[num[j] * i] = 1;
if(!(i % num[j]))
{
break;
}
}
}
}
int main(int argc, char *argv[])
{
int t;
fun();
while(cin >> t)
{
while(t--)
{
memset(flag, 0, sizeof(flag));
int n;
cin >> n;
int x, y;
int c = 0 ;
while(cin >> x >> y,(x||y))
{
int minn = min(x, y);
for(int i = 0; num[i] <= minn && num[i] <= n && i < s; i++)
{
if(x % num[i] == 0 && y % num[i] == 0)
{
for(int j = 1; j * num[i] <= n; j++)
{
flag[j * num[i]] = !flag[j * num[i]];
}
}
}
}
for(int i = 1; i <= n; i++)
{
if(!flag[i])
{
// cout << "i = " << i <<endl;
c++;
}
}
cout << c << endl;
}
}
return 0;
}
O题:
模拟题,建立一个临时的一个变化的然后按照题意模拟就行。
# include <iostream>
# include <cmath>
# include <vector>
# include <cstring>
using namespace std;
const int maxn = 105;
char ch[maxn][maxn];
char temp[maxn][maxn];
int dis[][2] = {0, 1, 0, -1, 1, 0, -1, 0};
int n, m, t;
//石头(R)、剪刀(S)、布(P)
void fun(char c, int x, int y)
{
for(int i = 0; i < 4; i++)
{
int fx = x + dis[i][0];
int fy = y + dis[i][1];
if(fx < 0 || fx >= n || fy < 0 || fy >= m)
{
continue;
}
if(c == 'R')
{
if(temp[fx][fy] == 'S')
{
ch[fx][fy] = 'R';
}
else if(temp[fx][fy] == 'P')
{
ch[x][y] = 'P';
}
}
else if(c == 'S')
{
if(temp[fx][fy] == 'P')
{
ch[fx][fy] = 'S';
}
else if(temp[fx][fy] == 'R')
{
ch[x][y] = 'R';
}
}
else if(c == 'P')
{
if(temp[fx][fy] == 'R')
{
ch[fx][fy] = 'P';
}
else if(temp[fx][fy] == 'S')
{
ch[x][y] = 'S';
}
}
}
}
int main(int argc, char *argv[])
{
while(cin >> n >> m >>t)
{
memset(temp,0, sizeof(temp));
memset(ch, 0, sizeof(ch));
for(int i = 0; i < n; i++)
{
cin >> ch[i];
strcpy(temp[i], ch[i]);
}
for(int k = 0; k < t; k++)
{
for(int i = 0; i < n; i++)
{
for(int j = 0; j < m ; j++)
{
char c = temp[i][j];
fun(c, i, j);
}
}
for(int i = 0; i < n; i++)
{
strcpy(temp[i], ch[i]);
}
}
for(int i = 0; i < n; i++)
{
cout << ch[i] << endl;
}
}
return 0;
}
P棋盘:
就是一个简单的模拟题,考验字符串的处理能力。
# include <iostream>
# include <cmath>
# include <vector>
# include <cstring>
using namespace std;
const int N = 8;
const int M = 8;
void process(vector<vector<char>> &vec, string state, string color)
{
for(int i = state.length() - 1; state[i] != ':'; i--)
{
if(state[i] == ',')
{
int x = state[i - 1] - '0' - 1;
int y = state[i - 2] - 'a';
char temp = (state[i - 3] == ',' || state[i - 3] == ':') ? 'p' : state[i - 3];
char ch = color == "White" ? toupper(temp) : tolower(temp);
vec[N - x - 1][y] = ch;
}
}
}
int main()
{
vector<vector<char>> vec(N, vector<char>(M, ' '));
string white, black;
getline(cin, white);
getline(cin, black);
process(vec, white + ",", "White");
process(vec, black + ",", "Black");
string line = "+---+---+---+---+---+---+---+---+";
cout << line << endl;
for(int i = 0; i < N; i++)
{
cout << "|";
for(int j = 0; j < M; j++)
{
char temp = vec[i][j];
if((i + j) & 1)
cout << ":" << (vec[i][j] == ' ' ? ':' : vec[i][j]) << ":";
else
cout << "." << (vec[i][j] == ' ' ? '.' : vec[i][j]) << ".";
cout << "|";
}
cout << endl;
cout << line << endl;
}
return 0;
}
Q题:
排个序找中间的就可以。
# include <iostream>
# include <cstdio>
# include <cstdlib>
# include <cstring>
# include <algorithm>
# include <functional>
# include <vector>
using namespace std;
int main(int argc, char *argv[])
{
int n;
while(cin >> n)
{
vector<int> a;
for(int i = 0; i < n; i++)
{
int x;
cin >> x;
a.push_back(x);
}
sort(a.begin(), a.end());
if(a.size() & 1)
{
cout << a[a.size() / 2] << endl;
}
else
{
cout << a[a.size()/ 2 - 1] <<endl;
}
}
return 0;
}
R题:
还是一个排序题。
# include <iostream>
# include <cstdio>
# include <cmath>
# include <algorithm>
# include <vector>
# include <string>
using namespace std;
int main(int argc, char *argv[])
{
int n;
while(cin >> n)
{
vector<int> a;
for(int i = 0; i < n; i++)
{
int x;
cin >> x;
a.push_back(x);
}
sort(a.begin(),a.end());
string str;
cin >> str;
int k;
cin >> k;
for(int i = 0; i < k; i++)
{
int x;
cin >> x;
cout << a[x - 1] << endl;
}
}
return 0;
}
S题:
一个排序题,先处理下字母然后映射一下之后就是找重复的咯,可以用map比较好做一点。
# include <iostream>
# include <cstring>
# include <string>
# include <algorithm>
# include <map>
using namespace std;
int f[8] = {2,3,4,5,6,7,8,9};
int main(int argc, char *argv[])
{
int n;
while(cin >> n)
{
map<string, int> s;
string str;
for(int i = 0; i < n; i++)
{
cin >> str;
for(int i = 0; i < str.size(); i++)
{
if(str[i] == 'R' || str[i] == 'S')
{
str[i] = 'P';
}
else if(str[i] == 'U' || str[i] == 'V')
{
str[i] = 'T';
}
else if(str[i] == 'X' || str[i] == 'Y')
{
str[i] = 'W';
}
}
int pos = str.find('-');
while(pos != -1)
{
str.erase(pos, 1);
pos = str.find('-');
}
for(int i = 0; i < str.size(); i++)
{
if(str[i] >= 'A' && str[i] <= 'Z')
{
int k = (str[i] - 'A')/3;
str[i] = '0' + f[k];
}
}
// cout << " str = " << str << endl;
map<string, int>:: iterator it = s.find(str);
if(it == s.end())
{
s.insert(make_pair(str, 1));
}
else
{
s[str]++;
}
}
for(map<string, int>::iterator it = s.begin(); it != s.end(); it++)
{
if(it->second > 1)
{
for(int i = 0; i < 3; i++)
{
cout << it->first[i];
}
cout << "-";
for(int i = 3; i< it->first.size(); i++)
{
cout << it->first[i];
}
cout << " " << it->second;
cout << endl;
}
}
}
return 0;
}
T题:
求出逆序数排序。
# include <iostream>
# include <cstring>
# include <algorithm>
# include <string>
using namespace std;
const int maxn = 105;
struct node
{
string str;
int flag;
int p;
}s[maxn];
bool cmp(struct node a, struct node b)
{
if(a.flag == b.flag)
{
return a.p < b.p;
}
return a.flag < b.flag;
}
int main(int argc, char *argv[])
{
int n, m;
while(cin >> n >> m)
{
memset(s, false, sizeof(s));
string str;
for(int i = 0; i < m; i++)
{
cin >> str;
int sum = 0;
for(int j = 0; j < n; j++)
{
for(int k = j + 1; k < n; k++)
{
if(str[j] > str[k])
{
sum++;
}
}
}
s[i].str = str;
s[i].flag = sum;
s[i].p = i;
}
sort(s, s + m, cmp);
for(int i = 0; i < m; i++)
{
cout << s[i].str << endl;
}
}
return 0;
}
U题:
统计重复的就可以,然后排个序。
# include <iostream>
# include <cstring>
# include <string>
# include <algorithm>
# include <map>
# include <iomanip>
using namespace std;
int main(int argc, char *argv[])
{
string str;
map<string, int> s;
int sum = 0;
while(getline(cin, str))
{
sum++;
s[str]++;
}
cout << setiosflags(ios::fixed) << setprecision(4);
for(map<string, int>:: iterator it = s.begin(); it != s.end(); it++)
{
cout << it->first << " " << setiosflags(ios::fixed) << setprecision(4) <<double(it->second)/ double(sum) * 100 << endl;
}
return 0;
}