Codeforces Round #561 (Div. 2) (还差2题)

总结:bitset的基本操作:http://www.cnblogs.com/RabbitHu/p/bitset.html

  B题中求每行每列均有...,只要在下一行中把上一行的第一个放到最后一个就能构造满足条件的解; 

  C题中这种,如果直接讨论绝对值的情况有点多,直接自己写几个例子试试会快上很多; 

  E题中用bitset处理这些集合是否重合特别的快,代码也很简洁;

题目链接:http://codeforces.com/contest/1166 

A:

题意:自己看看,练练英语,英语太菜了

题解:签到就行

#include <bits/stdc++.h>
using namespace std; 

int cnt[100];

int fun(int n)
{
    if(n==0 || n==1) return 0; 
    return (n-1)*n/2; 
}

int main()
{
    ios::sync_with_stdio(0);  cin.tie(0); cout.tie(0); 
    int n;  cin >> n;
    string str; 
    for(int i=1; i<=n; i++)
    {
        cin >> str;  
        cnt[str[0]-'a']++; 
    }
    long long sum=0;  
    for(int i=0; i<26; i++)
        sum+=fun(cnt[i]/2)+fun(cnt[i]-cnt[i]/2);
    cout<<sum<<endl; 
    return 0; 
} 
View Code

B:

题意:给出一个字符串的长度n,求这由这n个字符组成的矩阵能满足每一行每一列均有a e i o u 这5个字母,若能满足条件输出这个字符串(矩阵逐行输出即可), 找不到满足条件的字符就输出-1; 

题解:先求一下行和列,顺便判断一下。这个构造满足每一行每一列均有a e i o u,只要第一行能满足条件,把第一行的的第一个字符接到最后一个,作为下一行即可; 复杂度:O(n)

#include <bits/stdc++.h>
using namespace std;

string str, ans;
char ch[]={'a', 'e', 'i', 'o', 'u'};

int line, col;
bool myjudge(int k)
{
    for(int i=5; i*i<=k; i++)
    {
        if(k%i) continue;
        if(k/i>=5){
            line=k/i;
            col=i;
            return true;
        }
    }
    return false;
}

int main()
{
    ios::sync_with_stdio(0); cin.tie(0); cout.tie(0);
    int k; cin>>k;
    if(!myjudge(k))
        cout<<"-1"<<endl;
    else
    {
        for(int i=0; i<col; i++)
            str+=ch[i%5];
        for(int i=0; i<line; i++)
        {
            ans+=str;
            str=str.substr(1)+str[0];
        }
        cout<<ans<<endl;
    }
    return 0;
}
View Code

C:

题意:给一行数字,求能满足 abs(x+y)和abs(x-y) 所连成的区间(数轴上)包含abs(x) 和 abs(y) 所连成的区间的x,y有多少组;2n2e5

题解:很容易发现只要满足x<=2y这个条件即可,先排序,枚举最大的y即可,求y前面满足条件的所有x即可(注意这一层的x不是暴力的,直接找到一个满足条件的范围就行了); 

     复杂度:O(nlogn)

#include <bits/stdc++.h>
using namespace std; 

const int MAXN=2e6+5; 
int a[MAXN]; 

int main()
{
    int n; cin>>n; 
    for(int i=0; i<n; i++)
    {
        int data; cin>>data; 
        a[i]=abs(data); 
    }
    sort(a, a+n); 
    
    int pos=0; long long ans=0; 
    for(int i=0; i<n; i++)
    {
        while(pos<i && 2*a[pos]<a[i]) pos++; 
        ans+=i-pos; 
    }
    cout<<ans<<endl; 
    return 0; 
}
View Code

D:

感觉和数学联系很大,不会写;

E:

题意: 自己看,挺长的,练练英语

题解:直接判断是否 存在A所选择的集合是B所选择集合的子集即可,若存在就不满足条件,不存在就可以; 

#include <bits/stdc++.h>
using namespace std; 

const int MAXN=1e4+5; 
bitset<MAXN> a[55]; 
int n, m; 


int main()
{
    ios::sync_with_stdio(0); cin.tie(0); cout.tie(0); 
    //freopen("devin.txt", "r", stdin); 
    while(cin>>m>>n)
    {
        for(int i=0; i<m; i++)
        {
            a[i].reset();
            int k; cin>>k; 
            for(int j=0; j<k; j++)
            {
                int p; cin>>p; 
                a[i].set(p-1); 
            }    
        }
        
        for(int i=0; i<m-1; i++)
            for(int j=i+1; j<m; j++)
            {
                if((a[i]&a[j]).count()==0){
                    cout<<"impossible"<<endl; 
                    return 0;  
                }    
            }
        cout<<"possible"<<endl;
    }
    return 0; 
} 
View Code

猜你喜欢

转载自www.cnblogs.com/Yokel062/p/10914930.html