A. Problemsolving Log
簽到題,對於給出的字串,記錄每個字母出現的次數,然後遍歷一遍,如果對應的字母出現的次數大於它的位次,則說明該題被解出來了,最後輸出解題數量即可
點選檢視程式碼
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cmath>
#include<vector>
#include<map>
#include<queue>
#include<set>
using namespace std;
typedef long long ll;
const int N = 2*1e5 + 10;
void solve()
{
int n;
cin >> n;
string s;
cin >> s;
int st[27] = { 0 };
int count = 0;
for (int i = 0; i < s.size(); i++)
{
st[s[i] - 'A' + 1]++;
}
for (int i = 1; i < 27; i++)
{
if (st[i] >= i) count++;
}
cout << count << endl;
}
int main() {
int t;
cin >> t;
while (t--)
solve();
return 0;
}
B. Preparing for the Contest
排序問題,興奮 \(k\) 次,即前 \(1-k\) 按照升序排列,剩下的按照降序排序即可
點選檢視程式碼
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cmath>
#include<vector>
#include<map>
using namespace std;
typedef long long ll;
ll gcd(ll x, ll y) { //最大公約數
while (y ^= x ^= y ^= x %= y);
return x;
}
ll lcm(ll x, ll y) { //最小公倍數
return x * y / gcd(x, y);
}
void solve() {
int x, k;
cin >> x >> k;
int no = 0;
for (int i = 1; i<=x; i++)
{
if (k != 0)
cout << i << " ";
else
{
no = i;
break;
}
k--;
}
for (int i = x; i >= no; i--)
{
cout << i << " ";
}
cout << endl;
}
int main() {
int t;
cin >> t;
while (t--)
solve();
return 0;
}
C. Quests
暴力貪心,先用字首和預處理陣列 \(a\) ,之後對於陣列 \(b\) ,用一個陣列 \(d[i]\) 表示前 \(i\) 箇中最大的 \(b\) ,最後遍歷一遍, \(ans\) 取最大的 \(c[i] + (y-i)\times d[i]\)
點選檢視程式碼
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cmath>
#include<vector>
#include<map>
using namespace std;
typedef long long ll;
ll gcd(ll x, ll y) { //最大公約數
while (y ^= x ^= y ^= x %= y);
return x;
}
ll lcm(ll x, ll y) { //最小公倍數
return x * y / gcd(x, y);
}
void solve() {
ll x, y;
cin >> x >> y;
vector<ll>a(x+1);
vector<ll>b(x+1);
vector<ll>c(x + 1);
vector<ll>d(x + 1);
d[0] = 0;
c[0] = 0;
ll ans = 0;
for (int i = 1; i <=x; i++)
{
cin >> a[i];
c[i] = a[i] + c[i - 1];//字首和
// cout << c[i] <<" ";
}
for (int i = 1; i <=x; i++)
{
cin >> b[i];
d[i] = max(d[i - 1], b[i]);//最大
}
for (int i = 1; i <=min(x,y); i++)
{
ll sum = c[i] + (y - i) * d[i];
//cout << sum << " ";
ans = max(ans, sum);
}
cout << ans << endl;
}
int main() {
int t;
cin >> t;
while (t--)
solve();
return 0;
}
D. Three Activities
暴力打表,先將每一個活動都排序(找出最多人數的3天),然後這3天互相排列組合,去除天數相同的,剩下的找最大值即是答案
點選檢視程式碼
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cmath>
#include<vector>
#include<map>
using namespace std;
typedef long long ll;
const int N = 1e5 + 10;
ll gcd(ll x, ll y) { //最大公約數
while (y ^= x ^= y ^= x %= y);
return x;
}
ll lcm(ll x, ll y) { //最小公倍數
return x * y / gcd(x, y);
}
struct no {
ll num;
ll day;
}a[N],b[N],c[N];
bool cmp(no x, no y)
{
return x.num > y.num;
}
void solve() {
ll x;
cin >> x;
for (int i = 0; i < x; i++)
{
cin >> a[i].num;
a[i].day = i;
}
for (int i = 0; i < x; i++)
{
cin >> b[i].num;
b[i].day = i;
}
for (int i = 0; i < x; i++)
{
cin >> c[i].num;
c[i].day = i;
}
sort(a, a + x, cmp);
sort(b, b + x, cmp);
sort(c, c + x, cmp);//由大到小排序
ll ans = 0;
for (int i = 0; i < 3; i++)
{
for (int j = 0; j < 3; j++)
{
for (int k = 0; k < 3; k++)
{
if (a[i].day != b[j].day && a[i].day != c[k].day && b[j].day != c[k].day)
ans = max(a[i].num + b[j].num + c[k].num, ans);
}
}
}
cout << ans << endl;
}
int main() {
int t;
cin >> t;
while (t--)
solve();
return 0;
}
E. Game with Marbles
貪心排序問題,這一題 \(easy\) 和 \(hard\) 差別不大, \(easy\) 應該暴力模擬可以過。計算每一組的權值, \(Alice\) (簡稱 \(A\) ), \(Bob\) (簡稱 \(B\) ) 對於 \(A\) 來說,選擇的一組所獲得的權值是 \(a_i+b_i-1\) (消除 \(b_i\) 等於加 \(b_i\) 與 \(B\) 拉開了 \(b_i\) 的差距且保留了自己的剩餘的 \(a_i-1\) ,因此是 \(a_i+b_i-1\) );同理,對於 \(B\) 來說,也是這樣,因此無論是 \(A\) 操作時還是 \(B\) 操作時,所選擇的都是 \(a_i+b_i\) 最大值那一組 (每一組的權值都有 -1 因此可以僅比較 \(a_i+b_i\)) , 使用結構體儲存每一組石子的數量和和組號,對石子數量進行排序,之後由大到小進行模擬即可。
點選檢視程式碼
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cmath>
#include<vector>
#include<map>
using namespace std;
typedef long long ll;
const int N = 1e5 + 10;
ll gcd(ll x, ll y)
{ //最大公約數
while (y ^= x ^= y ^= x %= y);
return x;
}
ll lcm(ll x, ll y) { //最小公倍數
return x * y / gcd(x, y);
}
struct non {
ll num;
ll step;
}v[10];
bool cmp(non x, non y) {
return x.num < y.num;
}
void solve() {
ll x;
cin >> x;
vector<ll>a(x + 1);
vector<ll>b(x + 1);
// vector<ll>v(x + 1);
for (int i = 0; i < x; i++)
{
cin >> a[i];
}
for (int i = 0; i < x; i++)
{
cin >> b[i];
}
for (int i = 0; i < x; i++)
{
v[i].num = a[i] + b[i] - 1;
v[i].step = i;
}
sort(v, v + x,cmp);
//for (int i = 0; i < x; i++)
//{
// cout << v[i].num << " ";
//}
ll sum = 0;
int j = 1;
if (x % 2 == 0)
{
for (int i = x-1; i>=0; i--)
{
//cout << v[i] << " ";
if (j == 1)
{
sum += a[v[i].step] - 1;
}
else
sum -= b[v[i].step] - 1;
j *= -1;
}
}
else
{
for (int i = x - 1; i >= 0; i--)
{
if (i ==0)
{
sum += a[v[i].step] - 1;
break;
}
else
{
if (j == 1)
{
sum += a[v[i].step] - 1;
}
else
sum -= b[v[i].step] - 1;
}
j *= -1;
}
}
cout << sum << endl;
}
int main() {
int t;
cin >> t;
while (t--)
solve();
return 0;
}