• 2019HDU多校第四场题解


    1001.AND Minimum Spanning Tree

    传送门:HDU6614

    题意:给你一个又n个点的完全图,点编号从1~n,每条边的权值为被连接的两点编号按位与后的值。现在要你找到最小生成树,输出这个最小生成树的值 和 从2~n每个点相连的点(要求字典序最小)。

    题解:因为是进行二进制操作,我们把数写成二进制形式可以发现,对于一个数x我们找到其从最低位开始第一个0位i,&上只有这一位是1其他位为0的数时与的结果为0。显然,只有n为2的次方-1时最小生成树的值为1,其他情况下每个点都能找到按位与后结果为0的点相连。

    代码:

    #include <cstdio>
    using namespace std;
    int a[50]={1};
    int main() {
        int T,n;
        for (int i = 1; i < 30; i++)
            a[i] = a[i-1]*2;
        for (scanf("%d",&T);T--;) {
            scanf("%d",&n);
            int fg = 0;
            for (int i = 1; i < 30; i++)
                if (n+1 == a[i]) {
                    fg = 1;
                    break;
                }
            printf("%d
    ", fg);
            for (int i = 2; i <= n; i++) {
                int x = i,cnt = 1;
                while(x) {
                    if (x%2 == 0) break;
                    x>>=1;
                    cnt<<=1;
                }
                printf("%d%c",cnt>n?1:cnt,i==n?'
    ':' ');
            }
        }
        return 0;
    }
    View Code

    1003.Divide the Stones

    传送门:HDU6616

    题意:有n个石子,编号和重量都是1~n,现在要把这n个石子分成k组,要求每组数量和总重量相同,判断是否能分成k组,可以的话输出每组有哪些石子。

    题解:待补

    代码:

    1007.Just an Old Puzzle

    传送门:HDU6620

    题意:给你一个4*4的矩阵,问你120步内是否能复原。

    题解:奇数码可达性问题。我们判断将空格移到最后之后前15个数逆序对个数是否为偶数个即可。

    代码:

    #include <cstdio>
    using namespace std;
    const int N = 20 + 10;
    int a[5][5],b[N];
    int main() {
        int T,n;
        for (scanf("%d",&T);T--;) {
            int k=0,x=0;
            for (int i = 1; i <= 4; i++) 
                for (int j = 1; j <= 4; j++) 
                    scanf("%d",&a[i][j]);
            for (int i = 1; i <= 4; i++) {
                for (int j = 1; j <= 4; j++) {
                    if (i+j!=8&&!a[i][j]) {
                        for (int yy = j; yy < 4; yy++)
                            a[i][yy] = a[i][yy+1];
                        for (int xx = i; xx < 4; xx++)
                            a[xx][4] = a[xx+1][4];
                    }
                    b[++k] = a[i][j];
                }
            }
            for(int i=1;i<16;i++)
                for(int j=1;j<i;j++)
                    if(b[i]<b[j]) x++;
            if (x%2==0) printf("Yes
    ");
            else printf("No
    ");
        }
        return 0;
    }
    View Code

    1008.K-th Closest Distance

    传送门:HDU6621

    题意:你有一个长度为n的数组,有q次查询,每次询问[l,r]区间中p到ai第k大的距离是多少。

    题解:区间第k大,第一反应是主席树。我们可以二分距离mid,当(p-mid,p+mid)中元素个数有k个时,mid为答案。注意边界。

    代码:

    #include <bits/stdc++.h>
    #define ll long long
    using namespace std;
    const int N = 1e5 + 10;
    const int M = 1e6;
    struct node{
        int l,r,val;
    }T[N*40];
    int a[N],root[N],cnt;
    void update(int l,int r,int &x,int y,int pos) {
        T[++cnt] = T[y],T[cnt].val++,x = cnt;
        if (l == r) return;
        int mid = (l+r)>>1;
        if (mid >= pos) update(l,mid,T[x].l,T[y].l,pos);
        else update(mid+1,r,T[x].r,T[y].r,pos);
    }
    int query(int l,int r,int x,int y,int pl,int pr) {
        if (pl <= l && pr >= r) return T[y].val - T[x].val;
        int mid = (l+r)>>1;
        int ans = 0;
        if (pl <= mid) ans += query(l,mid,T[x].l,T[y].l,pl,pr);
        if (pr > mid) ans += query(mid+1,r,T[x].r,T[y].r,pl,pr);
        return ans;
    }
    int main() {
        int t,n,m;
        for (scanf("%d",&t);t--;) {
            scanf("%d%d",&n,&m);
            cnt = 0;
            T[0].l = 0;
            T[0].r = 0;
            T[0].val = 0;
            for (int i = 1; i <= n; i++) {
                scanf("%d",&a[i]);
                update(1,M,root[i],root[i-1],a[i]);
            }
            int X = 0;
            while(m--) {
                int l,r,p,k,L=0,R=M;
                scanf("%d%d%d%d",&l,&r,&p,&k);
                l^=X,r^=X,p^=X,k^=X;
                while(L<=R) {
                    int mid = (L+R) >> 1;
                    if (query(1,M,root[l-1],root[r],max(1,p-mid),min(M,p+mid))>=k){
                        X = mid;
                        R = mid - 1;
                    }else L = mid + 1;
                }
                printf("%d
    ", X);
            }
        }
        return 0;
    }
    View Code

    1010.Minimal Power of Prime

    传送门:HDU6623

    题意:给你一个大于一的正整数n,它可以写成不同质因子的幂的乘积的形式,现在问这些质因子的幂中,最小的幂是多少。

    题解:先暴力打出一万以内的素数,算出这些素数中最小的幂是多少,如果得到最小的幂为1或者n为1了则表示找出了最小幂,否则的话分类讨论。因为我们打了一万以内的素数,那么剩下的数最大也只能是一个素数的4次方,我们依次判断是否为某个数的4次方,3次方,2次方,都不是的话n应该是个素数答案为1 。(看到有人说先判断4次方再判断2次方然后判断3次方,好像顺序关系不大~

    代码:

    #include <cstdio>
    #include <cmath>
    #include <algorithm>
    #define ll long long 
    using namespace std;
    const int N = 1e4 + 10;
    const int INF = 0x3f3f3f3f;
    int prime[N];
    bool vis[N];
    int main(){
        int cnt = 0,T;
        for (int i = 2; i < N; i++) {
            if (!vis[i]) prime[cnt++] = i;
            for (int j = 2; i * j < N; j++)
                vis[i*j] = 1;
        }
        for (scanf("%d",&T);T--;) {
            ll n;
            scanf("%lld",&n);
            int ans = INF;
            for (int i = 0; i < cnt; i++) {
                if(n%prime[i] == 0) {
                    int num = 0;
                    while(n%prime[i]==0) {
                        num++;
                        n/=prime[i];
                    }
                    ans = min(ans,num);
                    if (ans == 1) break;
                }
            }
            if (ans == 1 || n == 1) {
                printf("%d
    ", ans);
                continue;
            }
            ll x = pow(n,0.25);
            if (pow(x,4) == n) 
                ans = min(ans,4);
            else if (pow(x+1,4) == n) ans = min(ans,4);
            else {
                x = pow(n,1.0/3.0);
                if (pow(x,3) == n) ans = min(ans,3);
                else if (pow(x+1,3) == n) ans = min(ans,3);
                else {
                    x = pow(n,0.5);
                    if (pow(x,2) == n) ans = min(ans,2);
                    else if (pow(x+1,2) == n) ans = min(ans,2);
                    else ans = min(ans,1);
                }
            }
            printf("%d
    ", ans);
        }
        return 0;
    }
    View Code
  • 相关阅读:
    1039 Course List for Student (25 分)
    1054 The Dominant Color (20 分)
    1065 A+B and C (64bit) (20 分)
    1046 Shortest Distance (20 分)
    1124 Raffle for Weibo Followers (20 分)
    第四章——scrapy爬虫
    scrapy命令行与shell
    表的插入,更新,删除,索引
    JQuery前端开发实战笔记
    今日回顾数据库
  • 原文地址:https://www.cnblogs.com/l999q/p/11285544.html
Copyright © 2020-2023  润新知