1. 程式人生 > >JZOJ5466. 【NOIP2017提高A組衝刺11.9】玩遊戲

JZOJ5466. 【NOIP2017提高A組衝刺11.9】玩遊戲

Description

小A得了憂鬱綜合症,小B正在想辦法開導她。
機智的小B決定陪著小A玩遊戲,他從魔法的世界裡變出一張無向聯通圖,每條邊上都有邊權。小B定義一條路徑的權值為所有經過邊中的最大權值,小A則定義兩點的最短路徑為所有路徑中權值最小的路徑權。
每次小A和小B會選出k對點mi_1,mi_2,分別計算出mi_1,mi_2的最短路徑ti,然後小B會拿出k堆靈魂寶石,每堆有ti個。然後小A先從一堆中選出若干個靈魂寶石拿走,接下來小B重複同樣的操作,如此反覆,直到取走最後一顆靈魂寶石,然後取走最後一顆寶石的人獲勝。
小B認為這樣遊戲太簡單,於是他會不定期向這張圖上加上一些邊,以增大遊戲難度。
小A具有預知未來的能力,她看到了自己和小B在未來遊戲中的選擇,以及小B增加的邊。現在對於每次遊戲,小A想知道自己是否存在必勝的方法。但是預知未來已經消耗了她太多精力,出於疲憊她只好找到了你。

Input

第一行三個數N和M和K,表示這張無向圖初始的點數與邊數,以及每次詢問的點對的個數;
接下來M行,每行三個數u,v,q,表示點u和點v之間存在一條權值為q的
邊;
接下來一行一個數Q,表示操作總數;
接下來Q行,表示操作,每行格式為下面兩條中的一條:
1.add u v q:表示在u與v之間加上一條邊權為q的邊;
2.game m1_1 m1_2 … mk_1 mk_2:表示一次遊戲中選擇的k對點。
資料保證1≤u,v,mi_1,mi_2≤n,1≤q,mi_1≠mi_2

Output

對於每個game輸出一行,若小A存在必勝策略,則輸出“madoka”,否則輸出“Baozika”,以回車結尾

Sample Input

5 6 2
1 2 3
2 3 6
4 2 4
5 3 5
3 4 5
5 1 5
4
game 1 3 4 3
game 1 5 2 4
add 2 5 4
game 1 5 3 4

Sample Output

Baozika
madoka
madoka

資料範圍

這裡寫圖片描述
首先,先要有一個結論,
如果寶石異或和為0,則先手輸,否則就先手贏。

簡單說一下吧,
如果不為0,則先手閉有一種方法使得它變為0,
當異或和為0的時候,無論怎樣都會改變。
最後的異或和一定是0的。

因為求最大邊權的最小值,
很顯然是最小生成樹。

加邊操作只有1000次,
每次暴力重構都沒有問題,
而詢問就用倍增lca解決。

code

#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cstdlib>
#include<cmath>
#define ll long long
#define N 5050
using namespace std;

char ch;
void read(int& n)
{
    n=0;
    for(ch=getchar();ch<'0' || ch>'9';ch=getchar());
    for(;'0'<=ch && ch<='9';n=(n<<3)+(n<<1)+ch-48,ch=getchar());
}
void readl(ll& n)
{
    n=0;
    for(ch=getchar();ch<'0' || ch>'9';ch=getchar());
    for(;'0'<=ch && ch<='9';n=(n<<3)+(n<<1)+ch-48,ch=getchar());
}

struct node
{
    int x,y;ll z;
}a[N],c[N*20];

bool cmp(node a,node b)
{
    return a.z<b.z;
}

int n,m,k,q,x,y,nxt[N*40],b[N],to[N*40],tot;
ll z,v[N*40],sum,g[N][13];
int fa[N],f[N][13],deep[N],t,f1,f2,useless;
bool bz[2*N],vis[N];

ll min(ll x,ll y){return x<y?x:y;}
ll max(ll x,ll y){return x>y?x:y;}

void ins(int x,int y,ll z)
{
    nxt[++tot]=b[x];
    to[tot]=y;
    v[tot]=z;
    b[x]=tot;
}

ll lca(int x,int y)
{
    ll mx=0;
    if(deep[y]>deep[x])swap(x,y);
    for(int i=12;i>=0;i--)
        if(deep[f[x][i]]>=deep[y])mx=mx<g[x][i]?g[x][i]:mx,x=f[x][i];

    if(x==y)return mx;

    for(int i=12;i>=0;i--)
        if(f[x][i]!=f[y][i])mx=mx<g[x][i]?g[x][i]:mx,x=f[x][i],mx=mx<g[y][i]?g[y][i]:mx,y=f[y][i];

    mx=mx<g[x][0]?g[x][0]:mx,mx=mx<g[y][0]?g[y][0]:mx;
    return mx;
}

void dfs(int x)
{
    vis[x]=0;
    //printf("%d\n",deep[x]);
    for(int i=b[x];i;i=nxt[i])
        if(vis[to[i]])
        {
            f[to[i]][0]=x;
            deep[to[i]]=deep[x]+1;
            g[to[i]][0]=v[i];
            dfs(to[i]);
        }
}

int get(int x)
{
    if(fa[x]!=x)fa[x]=get(fa[x]);
    return fa[x];
}

void reset()
{
    tot=t=0;sort(a+1,a+n+1,cmp);
    memset(b,0,sizeof(b));
    memset(vis,1,sizeof(vis));
    for(int i=1;i<=n;i++)
        fa[i]=i;
    for(int i=1;i<=n;i++)
    {
        f1=get(a[i].x);
        f2=get(a[i].y);
        if(f1!=f2)
        {
            ins(a[i].x,a[i].y,a[i].z);
            ins(a[i].y,a[i].x,a[i].z);
            fa[f2]=f1;
            t++;
        }else useless=i;
    }
    deep[1]=1;
    dfs(1);
    for(int j=1;j<13;j++)
        for(int i=1;i<=n;i++)
            f[i][j]=f[f[i][j-1]][j-1],g[i][j]=max(g[i][j-1],g[f[i][j-1]][j-1]);
} 

void pre()
{
    sort(c+1,c+1+m,cmp);
    for(int i=1;i<=n;i++)
        fa[i]=i;
    for(int i=1;t<n-1;i++)
    {
        f1=get(c[i].x);
        f2=get(c[i].y);
        if(f1!=f2)
        {
            fa[f2]=f1;
            t++;
            a[t]=c[i];
        }
    }
    a[n]=c[m];
}

int main()
{
    freopen("game.in","r",stdin);
    freopen("game.out","w",stdout);
    read(n);read(m);read(k);
    for(int i=1;i<=m;i++)
        read(c[i].x),read(c[i].y),readl(c[i].z);

    pre();
    reset();

    read(q);
    for(int i=1;i<=q;i++)
    {
        for(ch=getchar();ch!='g' && ch!='a';ch=getchar());
        if(ch=='g')
        {
            sum=0;
            for(int j=1;j<=k;j++)
                read(x),read(y),sum=sum^lca(x,y);
            if(sum)printf("madoka\n");else printf("Baozika\n");
        }
        else read(a[useless].x),read(a[useless].y),readl(a[useless].z),reset();
    }

    return 0;
}

相關推薦

JZOJ5466. NOIP2017提高A衝刺11.9遊戲

Description 小A得了憂鬱綜合症,小B正在想辦法開導她。 機智的小B決定陪著小A玩遊戲,他從魔法的世界裡變出一張無向聯通圖,每條邊上都有邊權。小B定義一條路徑的權值為所有經過邊中的最大權值,小A則定義兩點的最短路徑為所有路徑中權值最小的路徑權。

NOIP2017提高A衝刺11.9乘積

Description 豆豆最近在潛心研究數學,他發現了一類很有趣的數字,叫做無平方因子數。也就是這一類數字不能夠被任意一個質數的平方整除,比如6、7、10都是無平方因子數,而12則不是。 所以豆豆在思考一個問題——選擇不超過K個N以內的正整數乘起來,使得乘

NOIP2017提高A衝刺11.9總結

今天的比賽心情最不穩定。 T1:我看錯題了,原本看成乘積≤n,但是事實上並不是這樣。然後我就懵了,以為是容斥原理。但是容斥原理不是很熟,我就慌了。困惑我的一點是選的數互相制約的條件混亂。那麼可以利用八

JZOJ 5455NOIP2017提高A衝刺11.6拆網線

目錄: 題目: 分析: 程式碼: 題目: 傳送門 分析: 設f[i][0]f[i][0]表示在xx的子樹中,xx沒有被選擇的情況下最多有多少對點是兩兩配對的 f[

Jzoj5441NOIP2017提高A衝刺11.1序列

給定一個1~n的排列x,每次你可以將x1~xi翻轉。你需要求出將序列變為升序的最小操作次數。有多組資料。 此題十分不友善 對於多年沒有打過搜尋的蒟蒻更是如此 (強行)假定這個題資料範圍是在坑人(因為我

JZOJ 5441. NOIP2017提高A衝刺11.1序列

Description 給定一個1~n的排列x,每次你可以將x1~xi翻轉。你需要求出將序列變為升序的最小操作次數。有多組資料。 Input 第一行一個整數t表示資料組數。 每組資料第一行一個整數n,第二行n個整數x1~xn。 Output 每組

NOIP2017提高A衝刺11.6總結

今天的情況比昨天好了一些,但是還是有很大的進步空間。 我今天採用了迂迴的戰術,每一道題各想一點點。但是這樣是很不合理的,因為會打亂思緒。 接到題目,先去想第二題。(這是個梗) 第二題是一道構造題,肯定是從小到大排序,然後每個人找到合適的位置插進去。構造題不

NOIP2017提高A衝刺11.7總結

感覺上今天是信心題。所以絕對不能掉以輕心。 第一題想到了一個看似不是暴力的方法,先放著。打完第三題後發現可以直接上暴力,AC。 第二題是一個基於有向圖的裝壓DP,當時第一反應是spfa。所以直接打了

NOIP2017提高A衝刺11.8總結

今天的題目不難,但是我依然沒有拿到高分,信心題反而打擊了信心。 眼看著8場模擬賽已經過了7場,而每次成績都不是很理想,我不知道這樣的世界何時是一個盡頭! 第一題,肯定是貪心題,但是有點懵B,隨便想了

Jzoj5459NOIP2017提高A衝刺11.7密室

小X 正困在一個密室裡,他希望儘快逃出密室。 密室中有N 個房間,初始時,小X 在1 號房間,而出口在N 號房間。 密室的每一個房間中可能有著一些鑰匙和一些傳送門,一個傳送門會單向地創造一條從房間X

Jzoj5462NOIP2017提高A衝刺11.8好文章

nodgd寫了一篇文章,自認為這是一篇好文章。nodgd的文章由n個小寫英文字母組成。文章的一個子串指的是文章中的一段連續的字母,子串的長度就是這一段的字母個數。nodgd在文章中用了排比、對偶、前後

NOIP2017提高A衝刺11.2總結

不用說了,我連大眾分都沒拿到。不過做得好的一點是,該拿的分我都拿了。 第一題看了5秒就切了,這不就是拓補排序加個優先佇列嗎? 第二題:期望。我提醒自己不要慌,記得期望的線性性,即和的期望等於期望的和

JZOJ 5444. NOIP2017提高A衝刺11.2救贖

Description “是的。”我回答,“我不會忘記你。在森林裡我會一點點記起往日的世界。要記起的大概很多很多:各種人、各種場所、各種光、各種歌曲……” ——村上春樹《世界盡頭與冷酷仙境》 在沒有心存在的世界盡頭,音樂能夠使小鎮居民消散的心重新聚攏成形。

NOIP2017提高A衝刺11.2救贖(數學期望)

Description “是的。”我回答,“我不會忘記你。在森林裡我會一點點記起往日的世界。要記起的大概很多很多:各種人、各種場所、各種光、各種歌曲……” ——村上春樹《世界盡頭與冷酷仙境》 在沒有心存在的世界盡頭,音樂能夠使小鎮居民消散的心重新聚攏成形。

ZJOJ 5454NOIP2017提高A衝刺11.5仔細的檢查

Description nodgd家裡種了一棵樹,有一天nodgd比較無聊,就把這棵樹畫在了一張紙上。另一天nodgd更無聊,就又畫了一張。 這時nodgd發現,兩次畫的順序是不一樣的,這就導致了原本的某一個節點u0在第一幅圖中編號為u1,在第二副圖中編號為

NOIP2017提高A衝刺11.8購物

Description X 城的商場中,有著琳琅滿目的各種商品。一日,小X 帶著小Y 前來購物,小Y 一共看中了n件商品,每一件商品價格為Pi。小X 現在手中共有m個單位的現金,以及k 張優惠券。小X 可以在購買某件商品時,使用至多一張優惠券,若如此

JZOJ5455. NOIP2017提高A衝刺11.6拆網線

Description 企鵝國的網咖們之間由網線互相連線,形成一棵樹的結構。現在由於冬天到了,供暖部門缺少燃料,於是他們決定去拆一些網線來做燃料。但是現在有K只企鵝要上網和別人聯機遊戲,所以他們需要把這K只企鵝安排到不同的機房(兩隻企鵝在同一個機房會吵架),然

NOIP2017提高A衝刺11.1總結

The newest situation 這場模擬賽比之前的正式多了,非常考驗我。 在試機的那半個小時裡,應該去打一些模板。 接到題目,先讓自己鎮定下來。 看了第一題,發現結論肯定,可以直接用線段樹做。可是我忘了如果要線段樹的話,有一些細節要處理到位。具

JZOJ5460. NOIP2017提高A衝刺11.7士兵訓練

題目 Input 第一行兩個數n,q 表示士兵數以及閱兵次數。 接下來一行n-1 個整數,第i 個整數表示士兵i+1 的直屬教官。 接下來n 行每行兩個整數i i b ,l 描述一位士兵的屬性。 接下來q 行每行一個整數i s ,表示這次閱兵的

JZOJ5459. NOIP2017提高A衝刺11.7密室

Description 小X 正困在一個密室裡,他希望儘快逃出密室。 密室中有N 個房間,初始時,小X 在1 號房間,而出口在N 號房間。 密室的每一個房間中可能有著一些鑰匙和一些傳送門,一個傳送門會單向地創造一條從房間X 到房間Y 的通道。另外,想要通過