Codeforces Round #612 (Div. 2)
B题:
题意:一横排是一张牌,如果满足任意三张牌可以组成的每一列有三张相同的牌或者有三张不同的牌就可以组成一副牌,问能组成多少副这样的牌,打乱顺序算一副。
题解:我们通过两张牌来匹配第三章牌的方式来确定。
#include<bits/stdc++.h>
using namespace std;
const int N=1e3+505;
string arr[N];
map<string,int>mp;
int main()
{
int n,k; cin>>n>>k;
for(int i=1;i<=n;i++){
cin>>arr[i];
mp[arr[i]]++;
}
int ans=0;
for(int i=1;i<=n;i++){
for(int j=i+1;j<=n;j++){
string tmp="";
for(int m=0;m<k;m++){
if(arr[i][m]==arr[j][m]) tmp+=arr[i][m];
else{
if(arr[i][m]!='S'&&arr[j][m]!='S') tmp+='S';
else if(arr[i][m]!='T'&&arr[j][m]!='T') tmp+='T';
else tmp+='E';
}
}
ans+=mp.count(tmp);
}
}
cout<<ans/3<<endl;
}
C题:
题意:一串连续的灯泡,掉落下来了几个,现在需要我们重新弄上去。如果相邻的奇偶性不同那么我们答案就++。
题解:我们定义四个状态:当前的位置,可用的奇数,可用的偶数,当前位置是奇数还是偶数,我们奇数偶数不用单独枚举,如果我们知道我们当前位置前面的空位数,那么我用了多少奇数,另外的偶数个数一定是我们的空位数减去奇数个数。所以我们直接DP。
#include<bits/stdc++.h>
using namespace std;
const int inf=0x3f3f3f3f;
const int N=1e2+5;
int arr[N],b[N];
int f[105][105][105][3];
int main()
{
int n; cin>>n;
memset(f,inf,sizeof f);
int odd=n-n/2,even=n/2,sum=0;
for(int i=1;i<=n;i++){
cin>>arr[i];
if(arr[i]){
if(arr[i]%2==0) even--;
else odd--;
}
else sum++;
b[i]=sum;
}
if(!arr[1]){
f[1][1][0][1]=f[1][0][1][0]=0;
}else{
if(arr[1]&1) f[1][0][0][1]=0;
else f[1][0][0][0]=0;
}
for(int i=2;i<=n;i++){
for(int j=0;j<=b[i];j++){
int k=b[i]-j;
if(arr[i]){
if(arr[i]%2==0) f[i][j][k][0]=min(f[i-1][j][k][1]+1,f[i-1][j][k][0]);
else f[i][j][k][1]=min(f[i-1][j][k][1],f[i-1][j][k][0]+1);
} else{
if(j) f[i][j][k][1]=min(f[i-1][j-1][k][1],f[i-1][j-1][k][0]+1);
if(k) f[i][j][k][0]=min(f[i-1][j][k-1][1]+1,f[i-1][j][k-1][0]);
}
}
}
int ans;
if(arr[n]){
if(arr[n]&1) ans=f[n][odd][even][1];
else ans=f[n][odd][even][0];
}
else ans=min(f[n][odd][even][1],f[n][odd][even][0]);
cout<<ans<<endl;
}
D题:
题意:给n行,每行p,c,p代表这个而节点的父亲节点,c代表这个节点的子树中有多少个
a
j
a_j
aj严格小于这个节点的
a
i
a_i
ai。
题解:我们从根节点开始遍历,一直搜索到叶子节点,先把叶子节点放在容器中,然后我们把每个非叶子节点插入到x=c[u]这个位置,这样就能保证前面有c[u]个节点的值比我们小(因为我们最后赋值的时候是升序赋值)。
#include<bits/stdc++.h>
using namespace std;
const int N=2e3+5;
vector<int> g[N];
int c[N],a[N];
vector<int> dfs(int u)
{
vector<int> l;
for(int i=0;i<g[u].size();i++){
vector<int> d=dfs(g[u][i]);
for(int j=0;j<d.size();j++) l.push_back(d[j]);
}
if(c[u]>l.size()) {cout<<"NO"<<endl; exit(0);}
l.insert(l.begin()+c[u],u);
return l;
}
int main()
{
int n,rt; cin>>n;
for(int i=1;i<=n;i++){
int p; cin>>p>>c[i];
g[p].push_back(i);
if(!p) rt=i;
}
vector<int> ans=dfs(rt);
int cnt=0;
for(int i=0;i<ans.size();i++) a[ans[i]]=++cnt;
cout<<"YES"<<endl;
for(int i=1;i<=n;i++) cout<<a[i]<<' ';
}