• F. Beautiful Rectangle 构造


    F. Beautiful Rectangle

    题解:

    本来这个题目不准备写题解了的,因为这个确实不是很难,但是我wa了很多次之后,发现还是有写的必要。

    这个题目首先求出p和q,这个不是很难求,就是统计每一个数字的数量,然后排序一下,求出每一个宽 x 可以放进去的最多的数量。

    求出 p q之后就是构造一个解即可。

    但是这个构造要注意 一定是要 先构造小的!!!!

    这个是为什么呢?

    就看看3 5 感性理解一下吧

    1 4 7 10 13

    14 2 5 8 11

    12 15 3 6 9

    5 3

    1 6 11

    12 2 7

    8 13 3

    4 9 14

    15 5 10

    对于第二个 5和6 10和11是排在一块的,而对于第一个则没有这样的情况。

    #include <bits/stdc++.h>
    using namespace std;
    const int maxn = 4e5+10;
    typedef long long ll;
    int a[maxn],v[maxn],num[maxn],val[maxn],sum[maxn],c[maxn];
    map<int,int>mp[maxn];
    bool cmp(int a,int b){
    	return num[a]>num[b];
    }
    int main() {
        int n;
        scanf("%d", &n);
        for (int i = 1; i <= n; i++) {
            scanf("%d", &v[i]);
            a[i] = v[i];
            c[i]=i;
        }
        sort(v + 1, v + 1 + n);
        int len = unique(v + 1, v + 1 + n) - v - 1;
        for (int i = 1; i <= n; i++) {
            int pos = lower_bound(v + 1, v + 1 + len, a[i]) - v;
            num[pos]++, val[pos] = num[pos];
        }
        sort(val + 1, val + 1 + len);
        for (int i = 1; i <= len; i++) {
            int x = lower_bound(val + 1, val + 1 + len, i) - val;
    //        printf("i=%d x=%d val=%d
    ",i,x,val[i]);
            sum[i] = sum[i - 1] + len - x + 1;
        }
        int p = 1, q = 1, maxs = 0;
        for (int i = 1; i <= sqrt(n); i++) {
            int res = sum[i] / i * i;
            if(sum[i]/i<i) continue;
    //        printf("i=%d sum=%d res=%d
    ",i,sum[i],res);
            if (res > maxs) {
                maxs = res;
                p = i;
                q = sum[i] / i;
            }
        }
    //    printf("p=%d q=%d
    ",p,q);
        int sx = 0, sy = 0,now = 0;
        sort(c+1,c+1+len,cmp);
        for (int i = 1; i <= len; i++) {
        	int id = c[i];
            for (int j = 1; j <= min(p, num[id]); j++) {
                mp[sx][sy] = v[id];
                sy=(sy+1)%q, sx=(sx+1)%p;
                if(!sx){
                	++now;
                	sx = 0,sy = now;
    			}
            }
        }
        printf("%lld
    ",1ll*p*q);
        printf("%d %d
    ",p,q);
        for(int i=0;i<p;i++){
            for(int j=0;j<q;j++){
                printf("%d ",mp[i][j]);
            }
            printf("
    ");
        }
    }
    
  • 相关阅读:
    数据库 数据库编程二
    Linux 退格键不回显
    数据库 数据库编程一
    数据库 SQL语法二
    数据库 SQL语法一
    数据库 Linux下的MySQL数据库管理
    docker-compose
    winodws同步时间命令
    国内yum源的安装(163,阿里云,epel)
    postgresql双机热备、高可用方案(采用pacemaker+corosync实现)
  • 原文地址:https://www.cnblogs.com/EchoZQN/p/13393794.html
Copyright © 2020-2023  润新知