2022.5.6
Codeforces Round #786 (Div. 3)
A - Number Transformation
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
using namespace std;
typedef long long ll;
typedef pair<int,int> pii;
const int N=1e5+10,INF=1e9;
int main()
{
ios::sync_with_stdio(false);
cin.tie(0);
int t;
cin >> t;
while(t--)
{
int a,b;
cin >> a >> b;
if(a>b||b%a)
{
cout << "0 0\n";
}
else
{
int cnt = b / a;
cout << "1 "<<cnt<<'\n';
}
}
return 0;
}
B - Dictionary
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
#include<map>
using namespace std;
typedef long long ll;
typedef pair<int,int> pii;
const int N=1e5+10,INF=1e9;
int main()
{
ios::sync_with_stdio(false);
cin.tie(0);
int t;
cin >> t;
while(t--)
{
string s;
cin>>s;
int tot = s[0] - 'a';
int cnt = (s[0] - 'a' ) * 26-tot+(s[1]-'a'+1);
if(s[1]>s[0])
{
cnt--;
}
cout << cnt << '\n';
}
return 0;
}
C - Infinite Replacement
如果替换的串有a的话则可以无限替换(特判只有a一个字母的替换串),如果替换串没有a,则方案数为pow(2,a.length())种。
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
using namespace std;
typedef long long ll;
typedef pair<int,int> pii;
const int N=1e5+10,INF=1e9;
int main()
{
ios::sync_with_stdio(false);
cin.tie(0);
int t;
cin >> t;
while(t--)
{
string a;
string b;
cin >> a >> b;
if(b.length()==1&&b[0]=='a')
{
cout << "1\n";
continue;
}
int f = 0,ff = 0;
for (int i = 0; i < b.length();i++)
{
if(b[i]!='a')
{
f = 1;
}
else
ff = 1;
}
if(f&&!ff)
{
int len = a.length();
ll ans = pow(2,len);
cout << ans << '\n';
}
else
{
cout << "-1\n";
}
}
return 0;
}
D - A-B-C Sort
思路是对的,debug的时候没发现打错字母了
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
using namespace std;
typedef long long ll;
typedef pair<int,int> pii;
const int N=2e5+10,INF=1e9;
int a[N],b[N];
int main()
{
ios::sync_with_stdio(false);
cin.tie(0);
int t;
cin>>t;
while(t--)
{
int n;
cin>>n;
int f = 0;
for (int i = 1; i <= n;i++)
{
cin >> a[i];
}
memcpy(b, a, sizeof a);
sort(b + 1, b + 1 + n);
if(n&1)
{
if(a[1]!=b[1])
{
cout << "NO\n";
continue;
}
}
for (int i = n&1?2:1; i <= n; i+=2)
{
if((a[i]==b[i]&&a[i+1]==b[i+1])||(a[i]==b[i+1]&&a[i+1]==b[i]))
{
}
else
{
f = 1;
break;
}
}
if(f)
cout << "NO\n";
else
cout << "YES\n";
}
return 0;
}
E - Breaking the Wall
每次可以选择一个ai使得a[i]-2且a[i]相邻的数-1,问最少需要多少次操作使得数组至少有2个数<=0?。考虑到最后两个变成0的数,如果它们之间隔的很远,那么操作次数则为(a[i]+1)/2,(a[j]+1)/2,如果它们相邻,则分为两种情况:第一种,如果一个数是另外一个数的两倍以上,那么操作次数为(a[i]+1)/2,第二种,此时的操作次数为ceil(a[i]+a[j]/3.0),如果它们之间相隔1且二者均为奇数,则可以用一次操作让他们都-1,则二者变成偶数,此时花费为(a[i]/2)+(a[j]/2),比二者直接相除花费少1。
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
using namespace std;
typedef long long ll;
typedef pair<int,int> pii;
const int N=2e5+10,INF=1e9;
ll a[N], b[N];
int main()
{
ios::sync_with_stdio(false);
cin.tie(0);
int n;
cin>>n;
for (int i = 1; i <= n;i++)
{
cin >> a[i];
b[i] = a[i];
}
ll ans = 0;
sort(b + 1, b + 1 + n);
ans = (b[1]+1) / 2 + (b[2]+1) / 2;
for (int i = 2; i <= n - 1;i++)
{
if(a[i-1]%2 && a[i+1]%2)
{
ans = min(ans, (a[i - 1] - 1) / 2 + (a[i + 1] - 1) / 2 + 1);
}
}
for (int i = 1; i <= n - 1;i++)
{
ll x = a[i], y = a[i+1];
if(x < y)
swap(x, y);
if(x >= y*2)
{
ans = min(ans, (x + 1) / 2);
}
else
{
ans=min(ans,(ll)ceil((x + y)/3.0));
}
}
cout << ans;
return 0;
}
Codeforces Round #787 (Div. 3)
A - Food for Animals
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
using namespace std;
typedef long long ll;
typedef pair<int,int> pii;
const int N=1e5+10,INF=1e9;
int main()
{
ios::sync_with_stdio(false);
cin.tie(0);
int t;
cin>>t;
while(t--)
{
ll a,b,c;
ll x, y;
cin >> a >> b >> c >> x >> y;
int f = 0;
x -= a, y -= b;
if(c>=x+y)
f = 1;
if(f)cout << "yes\n";
else
cout << "no\n";
}
return 0;
}
B - Make It Increasing
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
using namespace std;
typedef long long ll;
typedef pair<int,int> pii;
const int N=1e5+10,INF=1e9;
ll a[N];
int main()
{
ios::sync_with_stdio(false);
cin.tie(0);
int t;
cin>>t;
while(t--)
{
int n;
cin>>n;
int f = 0;
for (int i = 1; i <= n;i++)
cin >> a[i];
ll cnt = 0;
for (int i = n-1; i >= 1;i--)
{
if(a[i]>=a[i+1])
{
while(a[i]>=a[i+1]&&a[i]!=0)
{
a[i] /= 2;
cnt++;
}
}
}
for (int i = 1; i <n ;i++)
{
if(a[i]>=a[i+1])
{
f = 1;
break;
}
}
if(f)
cout << "-1\n";
else
cout << cnt << '\n';
}
return 0;
}
C. Detective Task
答案即为最后一个1和第一个0位置相减+1
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
using namespace std;
typedef long long ll;
typedef pair<int,int> pii;
const int N=1e5+10,INF=1e9;
int main()
{
ios::sync_with_stdio(false);
cin.tie(0);
int t;
cin>>t;
while(t--)
{
string s;
cin>>s;
int n = s.length();
int pos1 = 0, pos0 = n-1;
int f = 0;
for (int i = 0; i < n;i++)
{
if(s[i]=='1')
{
pos1 = i;
}
if(s[i]=='0'&&!f)
{
f = 1;
pos0 = i;
}
}
int res = pos0 - pos1 + 1;
cout << res << '\n';
}
return 0;
}
D - Vertical Paths
从根节点开始dfs,走到叶节点路径加1.
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
#include<vector>
#include<map>
using namespace std;
typedef long long ll;
typedef pair<int,int> pii;
const int N=2e5+10,INF=1e9;
vector<int> p[N],path[N];
bool vis[N];
int cnt, ans;
void dfs(int x)
{
if(p[x].size()==0)
{
cnt++, ans++;
return;
}
for (int i = 0, j = p[x].size(); i < j; i++)
{
if(!vis[p[x][i]])
{
vis[p[x][i]] = 1;
path[cnt].push_back(p[x][i]);
dfs(p[x][i]);
}
}
return;
}
int main()
{
ios::sync_with_stdio(false);
cin.tie(0);
int t;
cin>>t;
while(t--)
{
cnt = ans = 0;
memset(vis,0,sizeof vis);
int n;
cin>>n;
int root = 0;
for (int i = 1; i <= n;i++)
{
int x;
cin >> x;
if(x==i)
root = i;
else
p[x].push_back(i);
}
path[0].push_back(root);
dfs(root);
cout << ans << '\n';
for (int i = 0; i < cnt; i++)
{
cout << path[i].size() << '\n';
for (int j = 0; j < path[i].size();j++)
{
cout << path[i][j] << ' ';
}
cout << '\n';
}
cout << '\n';
for (int i = 0; i <= n;i++)
{
p[i].clear();
path[i].clear();
}
}
return 0;
}
E - Replace With the Previous, Minimize
首先考虑贪心,必定是从前往后改变字典序才能最小,直到不够次数或者遍历完为止,每次改变记录哪些字母是需要改变的,最后输出的时候将字母改变即可。
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
using namespace std;
typedef long long ll;
typedef pair<int,int> pii;
const int N=1e5+10,INF=1e9;
bool vis[30];
int main()
{
ios::sync_with_stdio(false);
cin.tie(0);
int t;
cin>>t;
while(t--)
{
memset(vis, 0, sizeof vis);
int n, k;
cin>>n>>k;
string s;
cin >> s;
for (int i = 0, cnt = 0; i < n && cnt < k;i++)
{
while((s[i]!='a')&&!vis[s[i]-'a']&&cnt<k)
{
vis[s[i] - 'a'] = 1;
s[i]--;
cnt++;
}
}
for (int i = 0; i < n;i++)
{
while(vis[s[i]-'a'])
s[i]--;
cout << s[i];
}
cout << '\n';
}
return 0;
}