zoukankan      html  css  js  c++  java
  • 【AtCoder】ARC086

    C - Not so Diverse

    题解

    选出现次数K多的出来,剩下的都删除即可

    代码

    #include <bits/stdc++.h>
    #define fi first
    #define se second
    #define pii pair<int,int>
    #define pdi pair<db,int>
    #define mp make_pair
    #define pb push_back
    #define enter putchar('
    ')
    #define space putchar(' ')
    #define eps 1e-8
    #define mo 974711
    #define MAXN 200005
    //#define ivorysi
    using namespace std;
    typedef long long int64;
    typedef double db;
    template<class T>
    void read(T &res) {
        res = 0;char c = getchar();T f = 1;
        while(c < '0' || c > '9') {
    	if(c == '-') f = -1;
    	c = getchar();
        }
        while(c >= '0' && c <= '9') {
    	res = res * 10 + c - '0';
    	c = getchar();
        }
        res *= f;
    }
    template<class T>
    void out(T x) {
        if(x < 0) {x = -x;putchar('-');}
        if(x >= 10) {
    	out(x / 10);
        }
        putchar('0' + x % 10);
    }
    int N,K;
    int A[MAXN],cnt[MAXN],val[MAXN],tot;
    bool cmp(int a,int b) {
        return a > b;
    }
    void Init() {
        read(N);read(K);
        for(int i = 1 ; i <= N ; ++i) {
    	read(A[i]);
    	cnt[A[i]]++;
        }
    }
    void Solve() {
        for(int i = 1 ; i <= N ; ++i) {
    	if(cnt[i]) val[++tot] = cnt[i];
        }
        sort(val + 1,val + tot + 1,cmp);
        int ans = 0;
        for(int i = K + 1 ; i <= tot ; ++i) ans += val[i];
        out(ans);enter;
    }
    int main() {
    #ifdef ivorysi
        freopen("f1.in","r",stdin);
    #endif
        Init();
        Solve();
    }
    

    D - Non-decreasing

    题解

    用N - 1次操作把序列变成全正或者全负
    如果全负用处理成后缀和
    如果全正处理成前缀和

    代码

    #include <bits/stdc++.h>
    #define fi first
    #define se second
    #define pii pair<int,int>
    #define pdi pair<db,int>
    #define mp make_pair
    #define pb push_back
    #define enter putchar('
    ')
    #define space putchar(' ')
    #define eps 1e-8
    #define mo 974711
    #define MAXN 200005
    //#define ivorysi
    using namespace std;
    typedef long long int64;
    typedef double db;
    template<class T>
    void read(T &res) {
        res = 0;char c = getchar();T f = 1;
        while(c < '0' || c > '9') {
    	if(c == '-') f = -1;
    	c = getchar();
        }
        while(c >= '0' && c <= '9') {
    	res = res * 10 + c - '0';
    	c = getchar();
        }
        res *= f;
    }
    template<class T>
    void out(T x) {
        if(x < 0) {x = -x;putchar('-');}
        if(x >= 10) {
    	out(x / 10);
        }
        putchar('0' + x % 10);
    }
    int N;
    int a[MAXN];
    vector<pii > op;
    void Init() {
        read(N);
        for(int i = 1 ; i <= N ; ++i) read(a[i]);
    }
    void Solve() {
        int t = 1;
        for(int i = 2 ; i <= N ; ++i) {
    	if(abs(a[i]) > abs(a[t])) t = i;
        }
        for(int i = 1 ; i <= N ; ++i) {
    	if(i != t) {
    	    op.pb(mp(t,i));
    	    a[i] += a[t];
    	}
        }
        if(a[t] < 0) {
    	for(int i = N - 1 ; i >= 1 ; --i) {
    	    a[i] += a[i + 1];
    	    op.pb(mp(i + 1,i));
    	}
        }
        else {
    	for(int i = 2 ; i <= N ; ++i) {
    	    a[i] += a[i - 1];
    	    op.pb(mp(i - 1,i));
    	}
        }
        out(op.size());enter;
        for(auto k : op) {
    	out(k.fi);space;out(k.se);enter;
        }
    }
    int main() {
    #ifdef ivorysi
        freopen("f1.in","r",stdin);
    #endif
        Init();
        Solve();
    }
    

    E - Smuggling Marbles

    题解

    这个如果我们每个深度从每个点往上更新,更新的时候把儿子只有一个的点缩掉就显然不会超过(N log N),但是因为种种原因,在向上BFS的时候需要按深度从大到小排序
    题解说有(O(n))做法,我没细看

    代码

    #include <bits/stdc++.h>
    #define fi first
    #define se second
    #define pii pair<int,int>
    #define pdi pair<db,int>
    #define mp make_pair
    #define pb push_back
    #define enter putchar('
    ')
    #define space putchar(' ')
    #define eps 1e-8
    #define mo 974711
    #define MAXN 200005
    //#define ivorysi
    using namespace std;
    typedef long long int64;
    typedef double db;
    template<class T>
    void read(T &res) {
        res = 0;char c = getchar();T f = 1;
        while(c < '0' || c > '9') {
    	if(c == '-') f = -1;
    	c = getchar();
        }
        while(c >= '0' && c <= '9') {
    	res = res * 10 + c - '0';
    	c = getchar();
        }
        res *= f;
    }
    template<class T>
    void out(T x) {
        if(x < 0) {x = -x;putchar('-');}
        if(x >= 10) {
    	out(x / 10);
        }
        putchar('0' + x % 10);
    }
    const int MOD = 1000000007;
    int N,ans;
    int p[MAXN],dep[MAXN],pw[MAXN];
    vector<int> lay[MAXN];
    int vis[MAXN],tims,cnt[MAXN],dp[MAXN][2];
    vector<int> son[MAXN];
    int inc(int a,int b) {
        return a + b >= MOD ? a + b - MOD : a + b;
    }
    int mul(int a,int b) {
        return 1LL * a * b % MOD;
    }
    void update(int &x,int y) {
        x = inc(x,y);
    }
    int fpow(int x,int c) {
        int res = 1,t = x;
        while(c) {
    	if(c & 1) res = mul(res,t);
    	t = mul(t,t);
    	c >>= 1;
        }
        return res;
    }
    void Init() {
        read(N);
        for(int i = 1 ; i <= N ; ++i) read(p[i]);
        for(int i = 1 ; i <= N ; ++i) dep[i] = dep[p[i]] + 1;
        for(int i = 1 ; i <= N ; ++i) {
    	lay[dep[i]].pb(i);
        }
        pw[0] = 1;
        for(int i = 1 ; i <= N + 1 ; ++i) pw[i] = mul(pw[i - 1],2);
    }
    auto cmp = [](int a,int b){return dep[a] < dep[b];};
    priority_queue<int, vector<int>, decltype(cmp)> Q(cmp);
    void BFS() {
        while(!Q.empty()) {
    	int u = Q.top();Q.pop();
    	if(vis[p[u]] != tims) {
    	    Q.push(p[u]);
    	    vis[p[u]] = tims;
    	    son[p[u]].clear();
    	    dp[p[u]][0] = dp[p[u]][1] = 0;
    	}
    	if(son[u].size() == 1){
    	    if(u != 0) {
    		p[son[u][0]] = p[u];
    		son[p[u]].pb(son[u][0]);
    	    }
    	}
    	else if(u != 0) son[p[u]].pb(u);
    	if(son[u].size() > 1 || u == 0) {
    	    int s1 = 1,s2 = 1;
    	    for(auto v : son[u]) {
    		s1 = mul(s1,dp[v][0]);
    		s2 = mul(s2,inc(dp[v][0],dp[v][1]));
    	    }
    	    for(auto v : son[u]) {
    		update(dp[u][1],mul(s1, mul(fpow(dp[v][0], MOD - 2), dp[v][1])));
    	    }
    	    dp[u][0] = inc(s2, MOD - dp[u][1]);
    	}
        }
    }
    void Solve() {
        update(ans,pw[N]);
        for(int i = 1 ; i <= N ; ++i) {
    	if(!lay[i].size()) break;
    	++tims;
    	for(auto k : lay[i]) {
    	    Q.push(k);vis[k] = tims;
    	    dp[k][0] = 1;dp[k][1] = 1;
    	}
    	BFS();
    	update(ans,mul(dp[0][1], pw[N + 1 - lay[i].size()]));
        }
        out(ans);enter;
    }
    int main() {
    #ifdef ivorysi
        freopen("f1.in","r",stdin);
    #endif
        Init();
        Solve();
        return 0;
    }
    

    F - Shift and Decrement

    题解

    这题有点神仙啊QAQ

    首先,如果我们把除二认为是小数,最后再取整,结果也不变
    其次A操作进行最多60次就全0了
    所以我们认为第0次和第1次A之前的B操作有(p_0)个,第1次和第2次A之前的B操作有(p_1)个,到最后一次第(k)的次数(p_k)定义类似

    然后我们可以这么认为
    进行了(B)操作使得所有数减少了(P)
    (P = sum_{i = 0}^{k - 1} 2^{i}p_{k})

    然后进行(k)(A),并且取整

    然后进行(p_k)(B)

    (P)可以在取模(2^k)下进行,变成一次第三个操作,可以节约前两次用的操作数

    然后我们发现对于一个固定的(k),我们可以把每个数写成(A_{i} = 2^{k}B_{i} + C_{i})
    如果(P > C_{i}),这个数就是(B_{i} - p_k -1)
    否则这个数就是(B_{i} - p_k)

    所以我们按照余数大小排序,(P)在某个区间内是等价的

    我们要尽可能使第三种操作取值范围大,就要使前两种操作用的操作小,当我枚举一个k时,第二种用的操作数固定,我要找到(P)所在的区间([l,r])内二进制数位上1最少的数,可以用简单的数位dp实现

    枚举k,根据(P)取值不同,我们可以得到最多(61 * N)个序列
    只要求这些序列能减的最大值就行吗,不是的,有些序列通过相减会重复,我们需要把差分相同的序列分到一起
    然后做一下区间求并即可

    代码

    #include <bits/stdc++.h>
    #define fi first
    #define se second
    #define pii pair<int,int>
    #define pdi pair<db,int>
    #define mp make_pair
    #define pb push_back
    #define enter putchar('
    ')
    #define space putchar(' ')
    #define eps 1e-8
    #define mo 974711
    #define MAXN 200005
    //#define ivorysi
    using namespace std;
    typedef long long int64;
    typedef double db;
    template<class T>
    void read(T &res) {
        res = 0;char c = getchar();T f = 1;
        while(c < '0' || c > '9') {
    	if(c == '-') f = -1;
    	c = getchar();
        }
        while(c >= '0' && c <= '9') {
    	res = res * 10 + c - '0';
    	c = getchar();
        }
        res *= f;
    }
    template<class T>
    void out(T x) {
        if(x < 0) {x = -x;putchar('-');}
        if(x >= 10) {
    	out(x / 10);
        }
        putchar('0' + x % 10);
    }
    const int MOD = 1000000007;
    int N,tot;
    int64 K,a[205],rk[205];
    vector<pair<int64,int64> > range;
    int inc(int a,int b) {
        return a + b >= MOD ? a + b - MOD : a + b;
    }
    struct node {
        int64 c[205],u;
        friend bool operator == (const node &a,const node &b) {
    	for(int i = 2 ; i <= N ; ++i) {
    	    if(a.c[i] != b.c[i]) return false;
    	}
    	return true;
        }
        friend bool operator < (const node &a,const node &b) {
    	for(int i = 2 ; i <= N ; ++i) {
    	    if(a.c[i] != b.c[i]) return a.c[i] < b.c[i];
    	}
    	return false;
        }
        friend bool operator != (const node &a,const node &b) {
    	return !(a == b);
        }
    }seq[205 * 62];
    
    int minpopcount(int64 l,int64 r) {
        int dp[2][5];
        int cur = 0;
        for(int i = 0 ; i <= 3 ; ++i) dp[cur][i] = 1000000;
        dp[cur][3] = 0;
        for(int i = 60 ; i >= 0 ; --i) {
    	for(int j = 0 ; j <= 3 ; ++j) dp[cur ^ 1][j] = 100000;
    	int x = (l >> i) & 1,y = (r >> i) & 1;
    	for(int s = 0 ; s <= 3 ; ++s) {
    	    for(int k = 0 ; k <= 1 ; ++k) {
    		int t = 0;
    		if(s & 1) {
    		    if(k < x) continue;
    		    if(k == x) t |= 1;
    		}
    		if(s & 2) {
    		    if(k > y) continue;
    		    if(k == y) t |= 2;
    		}
    		dp[cur ^ 1][t] = min(dp[cur][s] + k,dp[cur ^ 1][t]);
    	    }
    	}
    	cur ^= 1;
        }
        int res = 100000;
        for(int i = 0 ; i <= 3 ; ++i) {
    	res = min(res,dp[cur][i]);
        }
        return res;
    }
    void Insert(int64 l,int64 r,int k) {
        int64 rem = K - k - minpopcount(l,r);
        if(rem < 0) return;
        int64 t = 1;
        while(k--) t *= 2;
        ++tot;
        for(int i = 1 ; i <= N ; ++i) {
    	seq[tot].c[i] = a[i] / t;
    	if(a[i] % t < l)  {
    	    seq[tot].c[i] -= 1;
    	    if(seq[tot].c[i] < 0) {--tot;return;} 
    	}
    	rem = min(rem,seq[tot].c[i]);
        }
        seq[tot].u = rem;
        for(int i = N ; i >= 2 ; --i) {
    	seq[tot].c[i] = seq[tot].c[i] - seq[tot].c[i - 1];
        }
    }
    void Solve() {
        read(N);read(K);
        int64 mv = 0;
        for(int i = 1 ; i <= N ; ++i) {read(a[i]);mv = max(mv,a[i]);}
        int up = 0;
        while(mv) {++up;mv >>= 1;}
        int64 t = 1;
        for(int i = 0 ; i <= up ; ++i) {
    	for(int j = 1 ; j <= N ; ++j) {
    	    rk[j] = a[j] % t;
    	}
    	sort(rk + 1,rk + N + 1);
    	rk[N + 1] = t - 1;
    	Insert(0,rk[1],i);
    	for(int j = 2 ; j <= N + 1 ; ++j) {
    	    if(rk[j] != rk[j - 1]) Insert(rk[j - 1] + 1,rk[j],i);
    	}
    	t *= 2;
        }
        sort(seq + 1,seq + tot + 1);
        range.pb(mp(seq[1].c[1] - seq[1].u,seq[1].c[1]));
        int ans = 0;
        for(int i = 2 ; i <= tot + 1; ++i) {
    	if(i == tot + 1 || seq[i] != seq[i - 1]) {
    	    sort(range.begin(),range.end());
    	    int64 st = range[0].fi,ed = range[0].se;
    	    for(int k = 1 ; k < range.size() ; ++k) {
    		if(range[k].fi > ed) {
    		    ans = inc(ans,(ed - st + 1) % MOD);
    		    st = range[k].fi;ed = range[k].se;
    		}
    		else ed = max(range[k].se,ed);
    	    }
    	    ans = inc(ans,(ed - st + 1) % MOD);
    	    range.clear();
    	}
    	range.pb(mp(seq[i].c[1] - seq[i].u,seq[i].c[1]));
        }
        out(ans);enter;
    }
    int main() {
    #ifdef ivorysi
        freopen("f1.in","r",stdin);
    #endif
        Solve();
        return 0;
    }
    
  • 相关阅读:
    Spark学习(一)Spark初识
    service mysqld restart mysqld: 未被识别的服务
    Spark学习(二)Spark 版本 WordCount
    java.sql.SQLException: Incorrect string value: '\xE4\xB8\xAD\xE9\x83\xA8' for column 'area' at row 1
    centos 6.8 yum源不可用安装报YumRepo Error: All mirror URLs are not using ftp, http[s] or file
    互联网运维装腔指南
    PHP生成一段时间之间的月份列表
    sql根据分组后排序取第一条数据
    sql 多行拼接 成一行
    js 常用汇总
  • 原文地址:https://www.cnblogs.com/ivorysi/p/10174137.html
Copyright © 2011-2022 走看看