• [HNOI 2013]比赛


    Description

    沫沫非常喜欢看足球赛,但因为沉迷于射箭游戏,错过了最近的一次足球联赛。此次联 赛共N支球队参加,比赛规则如下: 
    (1) 每两支球队之间踢一场比赛。 (2) 若平局,两支球队各得1分。 
    (3) 否则胜利的球队得3分,败者不得分。 
    尽管非常遗憾没有观赏到精彩的比赛,但沫沫通过新闻知道了每只球队的最后总得分, 然后聪明的她想计算出有多少种可能的比赛过程。 
    譬如有3支球队,每支球队最后均积3分,那么有两种可能的情况:
     可能性1    可能性2 
    球队  A  B  C  得分   球队 A  B  C  得分 
    A        -  3  0  3             A     -  0  3  3 
    B        0  -  3  3             B    3  -  0  3 
    C        3  0  -  3            C    0  3  -  3 
    但沫沫发现当球队较多时,计算工作量将非常大,所以这个任务就交给你了。请你计算 出可能的比赛过程的数目,由于答案可能很大,你只需要输出答案对109+7取模的结果

    Input

    第一行是一个正整数N,表示一共有N支球队。 接下来一行N个非负整数,依次表示各队的最后总得分。

    输入保证20%的数据满足N≤4,40%的数据满足N≤6,60%的数据满足N≤8,100%的数据 满足3≤N≤10且至少存在一组解。

    Output

    仅包含一个整数,表示答案对10^9+7取模的结果

    Sample Input

    4
    4 3 6 4

    Sample Output

    3

    题解

    我们令$f(l, r)$表示考虑$l$和$r$比赛,按$l$为主,若$l == r$,则$l++$。

    考虑直接爆搜的话,就是枚举当前的与之后的每一个比赛的结果是什么,但是复杂度很高。

    优化的话,考虑我枚举完一个的得分之后,剩下的状态打乱顺序不会影响最终结果,因为前面的贡献已经计算完毕了。

    那么我每次从小到大排序,并且把状态压起来,记忆化一下,就可以通过官方数据了,还有诸如鸡兔同笼和得分上限的剪枝也可以加。

     1 //It is made by Awson on 2017.10.11
     2 #include <set>
     3 #include <map>
     4 #include <cmath>
     5 #include <ctime>
     6 #include <cmath>
     7 #include <stack>
     8 #include <queue>
     9 #include <vector>
    10 #include <string>
    11 #include <cstdio>
    12 #include <cstdlib>
    13 #include <cstring>
    14 #include <iostream>
    15 #include <algorithm>
    16 #define LL long long
    17 #define Min(a, b) ((a) < (b) ? (a) : (b))
    18 #define Max(a, b) ((a) > (b) ? (a) : (b))
    19 #define sqr(x) ((x)*(x))
    20 using namespace std;
    21 const int MOD = 1000000007;
    22 
    23 int n, a[15];
    24 map<LL, int>mp[15];
    25 
    26 LL get_hash(int *a) {
    27     LL sum = 0;
    28     for (int i = 1; i <= n; i++)
    29         sum = sum*28+a[i];
    30     return sum;
    31 }
    32 int dfs(int *a, int l, int r) {
    33     if (3*(r-l) < a[l]) return 0;
    34     if (l == r) {
    35         if (l == n) return 1;
    36         int b[15]; for (int i = 1; i <= n; i++) b[i] = a[i];
    37         sort(b+1, b+n+1);
    38         LL tmp = get_hash(b);
    39         if (mp[l+1].count(tmp) == 1) return mp[l+1][tmp];
    40         return mp[l+1][tmp] = dfs(b, l+1, n);
    41     }
    42     int tol = 0;
    43     if (a[l] >= 3) {
    44         a[l] -= 3;
    45         (tol += dfs(a, l, r-1)) %= MOD;
    46         a[l] += 3;
    47     }
    48     if (a[l] >= 1 && a[r] >= 1) {
    49         a[l] -= 1, a[r] -= 1;
    50         (tol += dfs(a, l, r-1)) %= MOD;
    51         a[l] += 1, a[r] += 1;        
    52     }
    53     if (a[r] >= 3) {
    54         a[r] -= 3;
    55         (tol += dfs(a, l, r-1)) %= MOD;
    56         a[r] += 3;
    57     }
    58     return tol;
    59 }
    60 void work() {
    61     scanf("%d", &n);
    62     for (int i = 1; i <= n; i++)
    63         scanf("%d", &a[i]);
    64     sort(a+1, a+n+1);
    65     printf("%d
    ", dfs(a, 1, n));
    66 }
    67 int main() {
    68     work();
    69     return 0;
    70 }
  • 相关阅读:
    1-hadoop中遇到的各种异常
    13-hadoop-入门程序
    12-mapReduce的简介和yarn搭建
    11-hdfs-NameNode-HA-wtihQJM解决单点故障问题
    10-hdfs-hdfs搭建
    redis-java-api
    深度学习优化方法
    tf.nn.embedding_lookup()
    tf.variable_scope()和tf.name_scope()
    tf.Variable()、tf.get_variable()和tf.placeholder()
  • 原文地址:https://www.cnblogs.com/NaVi-Awson/p/7652956.html
Copyright © 2020-2023  润新知