Fork me on GitHub

2017-2018 ACM-ICPC German Collegiate Programming Contest (GCPC 2017)_组队训练

2017-2018 ACM-ICPC German Collegiate Programming Contest (GCPC 2017)

B Buildings

C Joyride

D Pants On Fire 

F Plug It In!

G Water Testing

I Überwatch 

K You Are Fired!

 

B Buildings

题意:给你m面墙,每面墙有n*n个格子,给你c种颜色,求有多种涂色方法(注意房子是一个正多边形,即旋转之后不能一样)

题解:polya计数裸题,

#include<bits/stdc++.h>
#define ll long long int
using namespace std;
const int mod = 1e9+7;
ll qpow(ll n,ll m)
{
    ll res=1;
    ll k=n;
    while(m)
    {
        if(m&1)res=res*k%mod;
        k=k*k%mod;
        m/=2;
    }
    return res;
}
int main()
{
    int n,m,c;
    cin>>n>>m>>c;
    ll sum = 0;
    ll g=qpow(c,n*n);
    for(int i=1;i<=m;i++)
    {
        sum+=(qpow(g,__gcd(i,m))%mod);
        sum = sum%mod;
    }
    sum=sum*qpow(m,mod-2)%mod;
    cout<<sum%mod<<endl;
}

C Joyride

题意:你在游乐园玩耍,你从1出发在x分钟内你要回到1,这中间有n个娱乐设施,m条人行道,你走人行道的时间要t分钟,m行输入两点之间的人行横道,n个游乐

设施所要花费的时间和价格,问你在x分钟内你可以花的最小钱为多少,x分钟都要用满,游乐设施可以多次玩耍。

题解:按花费钱的数量跑最短路,dist[v][k]dist[v][k] 表示在 kk 时刻走到点 vv 最少花费 dist[v][t]dist[v][t] 元。最短路变形,用队列来优化。

#include<bits/stdc++.h>
#define ll long long
using namespace std;
const int maxn = 1010;
int x;
int n,m,w;
int t[maxn],p[maxn];

struct Edge{
    int u,v,w;
    Edge(){}
    Edge(int _u,int _v){u=_u, v=_v;}
};
vector<Edge> E;
vector<int> G[maxn];
void addedge(int u,int v)
{
    E.push_back(Edge(u,v));
    G[u].push_back(E.size()-1);
}

struct Qnode
{
    int v,k,d;
    Qnode(){}
    Qnode(int _v,int _k,int _d) {
        v=_v, k=_k, d=_d;
    }
    bool operator<(const Qnode& oth)const {
        return d>oth.d;
    }
};
int dist[maxn][maxn];
bool vis[maxn][maxn];
void dijkstra()
{
    memset(dist,0x3f,sizeof(dist));
    memset(vis,0,sizeof(vis));

    priority_queue<Qnode> Q;
    if(t[1]<=x) dist[1][t[1]]=p[1];
    else return;
    Q.push(Qnode(1,t[1],p[1]));
    while(!Q.empty())
    {
        int u=Q.top().v, k=Q.top().k; Q.pop();
        if(vis[u][k]) continue;
        vis[u][k]=1;
        if(k+t[u]<=x && dist[u][k+t[u]]>dist[u][k]+p[u])
        {
            dist[u][k+t[u]]=dist[u][k]+p[u];
            Q.push(Qnode(u,k+t[u],dist[u][k+t[u]]));
        }
        for(int i=0;i<G[u].size();i++)
        {
            Edge &e=E[G[u][i]]; int v=e.v;
            if(k+w+t[v]>x) continue;
            if(!vis[v][k+w+t[v]] && dist[v][k+w+t[v]]>dist[u][k]+p[v])
            {
                dist[v][k+w+t[v]]=dist[u][k]+p[v];
                Q.push(Qnode(v,k+w+t[v],dist[v][k+w+t[v]]));
            }
        }
    }
}

int main()
{
    cin>>x>>n>>m>>w;
    for(int i=1,u,v;i<=m;i++)
    {
        cin>>u>>v;
        addedge(u,v);
        addedge(v,u);
    }
    for(int i=1;i<=n;i++) cin>>t[i]>>p[i];
    dijkstra();
    if(vis[1][x]) cout<<dist[1][x]<<endl;
    else cout<<"It is a trap."<<endl;
}

D Pants On Fire

题意:给你n条定理,输入格式确定,求m条问题的正确性。

题解:传递闭包。

#include<bits/stdc++.h>
#include<iostream>
#include<algorithm>
#include<cstring>
#include<vector>
#define ll long long int
#define mem(a,b) memset(a,b,sizeof a)
using namespace std;
const int INF = 0x3f3f3f3f;
map<string,int>mp;
int mm[404][404];
int n,m;
int ans;
void Floyd()
{
    for(int k=1;k<=ans;k++)
    {
        for(int i=1;i<=ans;i++)
        {
            for(int j=1;j<=ans;j++)
            {
                mm[i][j] = min(mm[i][j],mm[i][k]+mm[k][j]);
            }
        }
    }
}
int main()
{
    cin>>n>>m;
    ans = 1;
    mp.clear();
    for(int i=1;i<=2*n;i++)
    {
        for(int j=1;j<=2*n;j++)
        {
            if(i!=j) mm[i][j] = INF;
        }
    }
    for(int i=1;i<=n;i++)
    {
        string a,b,c,d,e;
        cin>>a>>b>>c>>e>>d;
        if(!mp[a])
        {
            mp[a] = ans;
            ans++;
        }
        if(!mp[d])
        {
            mp[d] = ans;
            ans++;
        }
        mm[mp[a]][mp[d]] = 1;
    }
    Floyd();
    while(m--)
    {
        string a,b,c,d,e;
        cin>>a>>b>>c>>e>>d;
        if(mp[a]==0||mp[d]==0)
        {
            puts("Pants on Fire");
            continue;
        }
        if(mm[mp[a]][mp[d]]==INF&&mm[mp[d]][mp[a]]==INF)
        {
            puts("Pants on Fire");
        }
        else if(mm[mp[a]][mp[d]]!=INF&&mm[mp[d]][mp[a]]==INF)
        {
            puts("Fact");
        }
        else{
            puts("Alternative Fact");
        }
    }
}

F Plug It In!

题意:n个插座,m个电器,下面k行匹配关系,一个一般的插座只能插一个电器,你可以使一个的插座插三个同一电器,求最大匹配数。

题解:先按插座的的型号进行匈牙利匹配,然后再枚举每一个型号的插座看看能不能再插电器,即再进行匈牙利匹配,二分图匹配。

#include<bits/stdc++.h>
#define ll long long int
#define mem(a,b) memset(a,b,sizeof a)
using namespace std;
int n,m,k;
int girl[1600],used[1600],love[1600][1600];
int tmp[1600];
void init()
{
    memset(girl,0,sizeof girl);
    memset(love,0,sizeof love);
    memset(used,0,sizeof used);
}
bool find(int x){
    int i,j;
    for (j=1;j<=n;j++){    
        if (love[x][j]==1 && used[j]==0)      
        {
            used[j]=1;
            if (girl[j]==0 || find(girl[j])) { 
                girl[j]=x;
                return true;
            }
        }
    }
    return false;
}
int find2(int h)
{
    for(int i=1;i<=n;i++)
    {
        if(used[i]||!love[h][i])continue;
        used[i]=1;
        if(tmp[i]!=h&&(tmp[i]==0||find2(tmp[i])))
        {
            tmp[i]=h;return 1;
        }
    }
    return 0;
}
int main()
{
    init();
    cin>>m>>n>>k;
    for(int i=1;i<=k;i++)
    {
        int x,y;
        cin>>x>>y;
        //mp[x[i]]++;
        love[x][y] = 1;
    }
    int ans = 0;
    for(int j=1;j<=m;j++)
    {
        mem(used,0);
        if(find(j)) ans++;
    }
    //cout<<ans<<endl;
    int ma=0;
    for(int i=1;i<=m;i++)
    {
        int add=0;
        for(int j=1;j<=n;j++)tmp[j]=girl[j];
        memset(used,0,sizeof(used));
        if(find2(i)){
            add++;
            memset(used,0,sizeof(used));
            if(find2(i))
            {
                    add++;
            }
        }
        ma=max(ma,add);
    }
    //cout<<ma<<" "<<ans<<endl; 
    printf("%d\n",ma+ans);
 } 

 G Water Testing

题意:按顺序给出边界的点,看看在封闭的图形内有多少个整数点。

题解: 皮克定理裸体,S=a+b/21,S表示多边形的面积 a表示多边形内的整数点 b表示多边形边界上的整数点。

//#include<bits/stdc++.h>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<iostream>
#include<string>
#include<vector>
#include<stack>
#include<bitset>
#include<cstdlib>
#include<cmath>
#include<set>
#include<list>
#include<deque>
#include<map>
#include<queue>
#define ll long long
#define MOD 1000000007
#define pdd pair<double,double>
#define mem(a,x) memset(a,x,sizeof(a))
#define IO ios::sync_with_stdio(false);cin.tie(0)
using namespace std;
const long long INF = 1e18+5;
const int inf = 0x3f3f3f3f;  
const double eps=1e-6;       
const int maxn=200005;    
const double pi=acos(-1);   
inline char nc() {static char buf[1000000],*p1=buf,*p2=buf;return p1==p2&&(p2=(p1=buf)+fread(buf,1,1000000,stdin),p1==p2)?EOF:*p1++;}
inline void read(int &sum) {char ch=nc();sum=0;while(!(ch>='0'&&ch<='9')) ch=nc();while(ch>='0'&&ch<='9') sum=(sum<<3)+(sum<<1)+(ch-48),ch=nc();}
ll gcd(ll a,ll b)
{
    if(b == 0)
        return a;
    return gcd(b,a%b);
}

ll x[maxn],y[maxn];
int n;
int main()
{
    int n;
    cin >> n;
    ll x0,y0,x1,y1,S = 0;
    cin >> x[1] >> y[1];
    x0 = x[1];
    y0 = y[1];
    x1 = x[1];
    y1 = y[1];
    for(int i=2;i<=n;i++) {
        cin >> x[i] >> y[i];
        S += (x1*y[i]-y1*x[i]);
        x1 = x[i];
        y1 = y[i];
    }
    S += (x1*y0-y1*x0);
    ll sum = 0;
   // cout<<S<<endl;
    for(int i=1;i<=n;i++){
       if(i<n){
        ll aa=abs(x[i+1]-x[i]);
        ll bb=abs(y[i+1]-y[i]);
        sum+=gcd(aa,bb)-1;
       }else{
        ll aa=abs(x[1]-x[n]);
        ll bb=abs(y[1]-y[n]);
        sum+=gcd(aa,bb)-1;
       }
    }
    sum+=n;
    printf("%lld\n",abs(S)/2+1-sum/2);
}

I Überwatch

签到题:

#include<bits/stdc++.h>
#define ll long long int
using namespace std;
int x[300030];
int dp[300030];
int main()
{
    int n,m;
    cin>>n>>m;
    for(int i=1;i<=n;i++)
    {
        cin>>x[i];
    }
    for(int i=1;i<=n;i++)
    {
        dp[i] = dp[i-1];
        if(i>=m+1)
        {
            dp[i] = max(dp[i-m]+x[i],dp[i]);
        }
    }
    int maxx = 0;
    for(int i=1;i<=n;i++)
    {
        maxx = max(maxx,dp[i]);
    }
    cout<<maxx<<endl;
}

K:

签到题

#include<bits/stdc++.h>
#define ll long long
using namespace std;
map<string,ll>mp;
typedef pair<string, ll> PAIR;
bool cmp(const PAIR &left,const PAIR &right)
{
    return left.second > right.second;
}
int main()
{
    ll n,d,k;
    cin>>n>>d>>k;
    ll ans = 0;
    for(int i=1;i<=n;i++)
    {
        string s;
        ll x;
        cin>>s>>x;
        mp[s] = x;
    }
    vector<PAIR> vec(mp.begin(),mp.end());
    sort(vec.begin(),vec.end(),cmp);
    for (vector<PAIR>::iterator it = vec.begin(); it != vec.end(); ++it)
    {
        if(d<=0) break;
        else{
            d-=it->second;
            ans++;
        }                 
    }
    if(ans>k||(ans==n&&d>0))
    {
        puts("impossible");
    }
    else{
        cout<<ans<<endl;
        ll q = 0;
        for (vector<PAIR>::iterator it = vec.begin(); it != vec.end(); ++it)
        {
            if(q>=ans) break;
            else{
                cout<<it->first<<", YOU ARE FIRED!"<<endl;
                q++;
             }                 
        }
    }
}

 

posted @ 2021-01-31 14:57  lcsdsg  阅读(125)  评论(0编辑  收藏  举报
【推荐】 程序员网址大全  |  EF CodeFirst  |  百度地图.NET  |  MyNPOI  |  开源  |  我的皮肤  |  ASP.NET MVC4  |  前端提升   |  LINQ   |  WCF   |  EasyUI  |