codeforces/contest/1228

Posted wjune-0405

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了codeforces/contest/1228相关的知识,希望对你有一定的参考价值。

B. Filling the Grid

分行和列进行染色,扫完图以后没有被染色的格子数,就是对答案产生的贡献值,wa了一发,因为没看清样例,会有冲突情况产生,这种情况下的答案是0

#include<bits/stdc++.h>
const double pi=3.14159;
typedef long long int ll;
const int mod=1e9+7;
int amap[1010][1010];
int hh[1010],ww[1010];
 
ll qpow(ll a,ll b)
ll res=1;
while(b>0)
    if(b&1)
 
        res=res*a%mod;
    
    b=b>>1;
    a=a*a%mod;
 

return res;

 
 
int main()
 
int h,w;
scanf("%d%d",&h,&w);
for(int i=1;i<=h;i++)
    scanf("%d",&hh[i]);

for(int i=1;i<=w;i++)
    scanf("%d",&ww[i]);

for(int i=1;i<=h;i++)
    for(int j=1;j<=hh[i];j++)
        amap[i][j]=1;
    
    amap[i][hh[i]+1]=-1;

 
for(int i=1;i<=w;i++)
    for(int j=1;j<=ww[i];j++)
            if(amap[j][i]==-1)
                printf("0\n");
                return 0;
            
            else
                amap[j][i]=1;
    
    if(amap[ww[i]+1][i]==1)
          printf("0\n");
        return 0;
    
    else
        amap[ww[i]+1][i]=-1;

 
int cnt=0;
for(int i=1;i<=h;i++)
    for(int j=1;j<=w;j++)
    //printf("%d ",amap[i][j]);
        if(amap[i][j]==0)
            cnt++;
    
    //printf("\n");

//printf("cnt:%d\n",cnt);
 
 
    printf("%lld",qpow(2,cnt));
 
return 0;

C. Primes and Multiplication

定义了三种操作 

 g(x,p)、 f(x,y)、prime(x)

1、prime(x)定义为x的素因数集合。

Let prime(x)prime(x) be the set of prime divisors of xx. For example, prime(140)=2,5,7prime(140)=2,5,7, prime(169)=13prime(169)=13.

2、g(x,p)定义为出x的因数,这个因数是p的k次,并且k要最大。

Let g(x,p) be the maximum possible integer pkpk where kk is an integer such that xx is divisible by pkpk. For example:

  • g(45,3)=9 (45 is divisible by 3^2=9 but not divisible by 3^3=27),
  • g(63,7)=7 (63 is divisible by 7^1=7 but not divisible by 7^2=49).

3、f(x,y)定义为g(y,p)的乘积,p为prime(x)集合中的元素。

Let f(x,y) be the product of g(y,p)g(y,p) for all in prime(x)prime(x). For example:

  • f(30,70)=g(70,2)g(70,3)g(70,5)=2^13^05^1=10
  • f(525,63)=g(63,3)g(63,5)g(63,7)=3^25^07^1=6

 最后给出一个x,n,求出f(x,1)*f(x,2)……*f(x,n)的乘积

数据范围:The only line contains integers x and n (2x10^9 1n10^18) — the numbers used in formula.

题目很复杂,看完脑壳疼。

慢慢分析

1、对于给定的x,我们可以先进行质因数分解,因为早晚要用到

2、最后求的是多个f(x,y)的乘积,所以连乘中的1是可以被忽略的,那么怎么样才会产生1呢?

显然,对于g(y,p)来说,p本身不是y的因数,那么就会是1

3、这时候我们会自然的想到,对于1~n这个区间来说,以Pi为因数的数的乘积就是答案

例如对于x=6,n=11

prime(x)=2,3;

那么所以求得就是g(1,2)*g(2,2)*g(3,2)……*g(11,2)*g(1,3)*f(2,3)……*g(11,3)

这时候我们就可以发现,

2,6,10的贡献是2,2^1;

4的贡献是4,2^2;

8的贡献是8,2^3;

3,6的贡献是3,3^1;

9的贡献是9,3^2;

这时候题目就变成了,求出1~n中,所有数的最大素因数以及素数的次方数因数的乘积。

再看题面时,我们会发现素数范围在1^9,一个欧拉筛筛不出范围(可能有改进一下可以筛出的办法,但是我太菜了,并想不出)

但是再思考一下,1e5*1e5=1e10>1e9所以只要筛出1e5范围内的所有素数,最后看一下这个数本身是不是素数就可以了。

另外一个问题就是素数的最大次方数因数,2这个因数,对于4的时候,贡献就是4,对于8这个数,贡献就是8,我也不知道该怎么计算,最后看了网上别人的博客

虽然看懂了处理方法,但是并不知道什么原理,也说不清楚,反正以后就这么用吧。

反正没毛病。

#include<iostream>
#include<algorithm>
#include<cmath>
#include<cstdio>
#include<string.h>
#include<set>
using namespace std;
const double pi = 3.14159;
typedef long long int ll;
const int mod = 1e9 + 7;
long long int maxn = 1e5, m, n;
bool number[100005];
ll prime1[100005];
ll prime[100005];
int c = 0;
int c1 = 0;
void isprime()

 
    int i, j;
    memset(number, true, sizeof(number));
    for (i = 2; i <= maxn; i++)
    
        if (number[i]) 
            prime[c++] = i;
 
        
        for (j = 0; j<c&&prime[j] * i <= maxn; j++)
        
            number[prime[j] * i] = false;
 
            if (i%prime[j] == 0) //保证每个合数只会被它的最小质因数筛去,因此每个数只会被标记一次
                break;
        
    

 
ll qpow(ll a, ll b) 
    ll res = 1;
    while (b>0) 
        if (b & 1)
            res = res*a%mod;
        b=b>>1;
        a = a*a%mod;
    
    return res;

 
int main() 
    isprime();
    scanf("%lld %lld", &m, &n);
    for (int i = 0; i<c; i++) 
        if (m<prime[i])
            break;
        if(m%prime[i] == 0)
            prime1[c1++] = prime[i];
        
        while(m%prime[i]==0)
            m/=prime[i];
    
    if(m>1)
        prime1[c1++]=m;
    ll x;
    ll ans = 1;
    ll cnt = 0;
 
    for (int i = 0; i<c1; i++) 
        x = n;
        cnt = 0;
        while (x) 
            cnt += x / prime1[i];
            x /= prime1[i];
        
        ans = ans*qpow(prime1[i], cnt) % mod;
    
    printf("%lld\n", ans);
 
    return 0;

D. Complete Tripartite

给一张图

有点和边,没有重边,没有自环,

分成三个集合,每个集合里的元素互相不相连,和另两个图的元素一一相连。

这不是扫一遍染色就完事了?

还是wa了一发,有可能一条边都没有,也有可能是边数不够,有些点没用到

加个vis和cnt维护

暴力出奇迹!

#include<iostream>
#include<algorithm>
#include<cmath>
#include<cstdio>
#include<string.h>
#include<set>
using namespace std;
const double pi = 3.14159;
typedef long long int ll;
const int mod = 1e9 + 7;
long long int maxn = 1e5 + 9;
int n, m;
int color[300005];
int vis[300005];
int cnt1, cnt2, cnt3;
struct node 
    int s, t;
p[300005];
bool cmp(node a, node b) 
    if (a.s == b.s)
        return a.t < b.t;
    else
        return a.s < b.s;

int main() 
    scanf("%d %d", &n, &m);
    int a, b;
    for (int i = 1; i <= n; i++)color[i] = 1;
    for (int i = 1; i <= m; i++) 
        scanf("%d %d", &a, &b);
        vis[a]++;
        vis[b]++;
 
        p[i].s = min(a, b);
        p[i].t = max(a, b);
 
    
    sort(p + 1, p + 1 + m, cmp);
    for (int i = 1; i <= m; i++) 
        a = p[i].s, b = p[i].t;
        if (color[a] != color[b])
            continue;
        else 
            if (color[a] == 3)
            
                printf("-1\n");
                return 0;
            
            else 
                color[b] = color[a] + 1;
            
        
    
    for (int i = 1; i <= n; i++) 
        if (color[i] == 1)
            cnt1++;
        else if (color[i] == 2)
            cnt2++;
        else
            cnt3++;
    
    if (cnt1 == 0 || cnt2 == 0 || cnt3 == 0) 
        printf("-1\n");
        return 0;
    
    for (int i = 1; i <= n; i++) 
        if (color[i] == 1 && vis[i] == cnt2 + cnt3&&vis[i]) 
        else if (color[i] == 2 && vis[i] == cnt1 + cnt3&&vis[i]) 
        else if (color[i] == 3 && vis[i] == cnt1 + cnt2&&vis[i]) 
        else 
            printf("-1\n");
            return 0;
        
    
    for (int i = 1; i <= n; i++)
        printf("%d ", color[i]);
    return 0;

 

以上是关于codeforces/contest/1228的主要内容,如果未能解决你的问题,请参考以下文章

301重写域名.co.uk至网址:www.domain.co.uk就像搜索引擎友好的开发人员你!

co函数库源码解析

co co a P o a d s的使用

C# 处理来自 ipdata.co 的 JSON

下载类似 mega.co.nz 的文件

CO 353 - Homework assignment 4