zoukankan      html  css  js  c++  java
  • ACM学习历程—Hihocoder编程之美测试赛B题 大神与三位小伙伴(组合数学 )

    时间限制:2000ms
    单点时限:1000ms
    内存限制:256MB

    描述

    给你一个m x n (1 <= m, n <= 100)的矩阵A (0<=aij<=10000),要求在矩阵中选择一些数,要求每一行,每一列都至少选到了一个数,使得选出的数的和尽量的小。

    输入

    多组测试数据。首先是数据组数T

    对于每组测试数据,第1行是两个正整数m, n,分别表示矩阵的行数和列数。

    接下来的m行,每行n个整数,之间用一个空格分隔,表示矩阵A的元素。

    输出

    每组数据输出一行,表示选出的数的和的最小值。

    数据范围

    小数据:1 <= m, n <= 5

    大数据:1 <= m, n <= 100

    样例输入
    2
    3 3
    1 2 3
    3 1 2
    2 3 1
    5 5
    1 2 3 4 5
    5 1 2 3 4
    4 5 1 2 3
    3 4 5 1 2
    2 3 4 5 1
    
    样例输出
    Case 1: 3
    Case 2: 5
    

    题目大意是有三类纪念品A、B、C。每类纪念品又有N种不同的纪念品Ai、Bi、Ci(1 <= i <= N),然后对于Ai纪念品的剩余个数CAi是N+1-i个,对于Bi纪念品的剩余个数CBi是N+1-i个,Ci纪念品的剩余个数CCi是N+1-i个。

    要求拿出三件纪念品Ap, Bq, Ck,不能恰好有两件价值相同,求取法数。

    可以从两个角度考虑:

    (1)       从正面角度考虑:

    不能恰好有两件价值相同,那么就是三件价值都相同或者都不同。

    1.  三件价值都相同:

    假设我都取价值为i的纪念品,那么就有CAi*CBi*CCi可以取(CAi、CBi、CCi分别为Ai、Bi、Ci剩余个数)

    所以总数便是

    2.三件价值都不同:

             假设我A取了价值为i的纪念品,那么有CAi种;

    那么B不能取价值为i的,假设B取了价值为j的,有CBj种;

    那么C不能取价值为i和j的。

    所以总数便是

    此处说明一下,第一个式子是取A乘取B乘取C(取C是在C总数的基础上减去价值为i和j的)

    第二个式子就是第一个式子变形的,将n+1-i替换为i’,同理的j和k。

    第三个式子就是把i != j这个条件体现出来。

    接下来进一步化简:

    所以总的就是上面两种情况相加,得到

    然后由下面三组式子便可以求解:

    (2)       从反面角度考虑:

    不能恰好有两件价值相同,那么就是总选数里面减去它就OK了。

    总选数自然就是:

    恰好有两件价值相同,那么就先从ABC三个里选出两种准备选价值相同的i,选法有C(2, 3),即3种。

    然后剩余的一个不能选价值为i的,所以总数:

    所以最后答案就是:

    与第一种方法的答案一致。

    代码:

    #include <iostream>
    #include <cstdio>
    #include <cstdlib>
    #include <cmath>
    #include <cstring>
    #include <algorithm>
    #include <set>
    #include <map>
    #include <vector>
    #include <queue>
    #include <string>
    #define inf 0xfffffff
    #define eps 1e-10
    #define N 1000000007
    
    using namespace std;
    
    long long n, C1, C2;
    
    void Init()
    {
        n %= N;
        C1 = (n+1)*n/2;
        C1 %= N;
        C2 = (n+1)*n/2;
        if (C2%3 == 0)
        {
            C2 /= 3;
            C2 %= N;
            C2 *= 2*n+1;
            C2 %= N;
        }
        else
        {
            C2 %= N;
            C2 *= (2*n+1)/3;
            C2 %= N;
        }
    }
    
    long long ans()
    {
        long long s = (C1*C1) % N;
        s = (s*C1)%N + (3*s)%N - (3*((C1*C2)%N))%N;
        return (s%N+N)%N;
    }
    
    int main()
    {
        //freopen("test.txt", "r", stdin);
        int T;
        scanf("%d", &T);
        for (int times = 1; times <= T; ++times)
        {
            scanf("%lld", &n);
            printf("Case %d: ", times);
            Init();
            printf("%lld
    ", ans());
        }
        return 0;
    }
  • 相关阅读:
    Amount of Degrees(数位dp)
    【BZOJ2820】【XSY1721】GCD(莫比乌斯反演)
    【XSY2671】【BZOJ2693】jzptab(莫比乌斯反演)
    【模板】莫比乌斯反演
    CDQ分治&&整体二分
    线性方程组之高斯消元
    矢量及【模板】二维凸包
    回收数据表Ⅰ
    Spring的bean管理(注解)
    jquery与ajax的XMLHttpRequest对象介绍
  • 原文地址:https://www.cnblogs.com/andyqsmart/p/4509650.html
Copyright © 2011-2022 走看看