zoukankan      html  css  js  c++  java
  • 记一道毒瘤的数学题

    这种数学数数计算题搞到计算机上就变的很简单了。。。。

    可以暴力 (dfs) (O(3^{15})) 也可以简单 (DP) (O(15*m)) (m) 是边数。

    (f_{i,j}) 为走 (i) 步到 (j) 的方案数,每层递推即可。

    #include <iostream>
    #include <cstdio>
    using namespace std;
    
    int m;
    
    int g[40][2], f[16][10];
    
    void add(int u, int v) {
    	u -= 'A', v -= 'A';
    	g[++m][0] = u, g[m][1] = v;
    }
    
    int main() {
    
    	add('A', 'J'); add('J', 'A');
    	add('B', 'I'); add('I', 'B');
    	add('C', 'H'); add('H', 'C');
    	add('D', 'G'); add('G', 'D');
    	add('E', 'F'); add('F', 'E');
    	add('A', 'B');
    	add('B', 'C');
    	add('C', 'D');
    	add('D', 'E');
    	add('E', 'A');
    	add('F', 'G');
    	add('G', 'H');
    	add('H', 'I');
    	add('I', 'J');
    	add('J', 'F');
    
    	f[0][0] = 1;
    	for (int i = 1; i <= 15; i++) {
    		for (int j = 1; j <= m; j++) {
    			int u = g[j][0], v = g[j][1];
    			f[i][v] += f[i - 1][u];
    		}
    	}
    	printf("%d
    ", f[15][0]);
    	return 0;
    }
    

    得出结论 (3004)

    前置知识:

    组合数

    (C_a^{b}) 表示从 (a) 里面选 (b) 个,忽略顺序的方案数。(公式请自行百度组合数)

    隔板法

    (a) 个完全相同的物品分成 (k) 组,每组至少有一个物品的方案数。

    (a) 个物品排成一列,相邻两个之间想象有一个隔板,相当于从这 (a - 1) 个隔板里选出 (k - 1) 个隔板忽略顺序。

    分出的 (k) 份就是答案。

    故公式为 (C_{a - 1}^{k - 1})

    线性方程组的正整数解方案数

    (x_1 + x_2 + ...+x_n = m) 的正整数解。

    看做 (m) 个物品分成 (n) 份即可,代公式 (C_{m - 1}^{n - 1})

    线性方程组的非负整数解方案数

    (x_1 + x_2 + ...+x_n = m) 的非负整数解。

    (y_i = x_i + 1)

    变换一下为求 (y_1 + y_2 + ... y_n = m + n) 的正整数解。

    带入上次的公式即为 (C_{n + m - 1}^{n - 1})

    hhhh我相信没人能看懂我写的这么个破玩意的。

    猪脑子不会做这题。

    先进行一步转化:

    (A, B, C, D, E) 视为 (0, 1, 2, 3, 4)

    (J, I, H, G, F) 视为 (0', 1', 2', 3', 4')

    下面所述一切操作在 (mod 5) 意义下

    • 一次从内外转换:在 (i)(i')之间相互切换。

    • 在内圆走:(i Rightarrow i + 1)

    • 在外圆走:(i Rightarrow i - 1)

    初始状态 (0')。目标状态 (0')。求进行 (15) 次操作成功抵达目标状态的方案数。


    设在内圈逆时针走了 (a) 步,在外圈顺时针走了 (b) 步,外圈内圈上反复横跳走了 (c) 步。

    限制条件:

    1. (a + b + c = 15)

    2. (c) 是偶数。若 (c) 是奇数,最后会停在外圈

    3. 由第二题限制,可知 (a + b) 为奇数。

    4. (a) 对位置的数值贡献是 (+a)(b) 的贡献是 (-b)。为了保证最终停在 (0),需要保证 (a equiv b pmod 5)

    经过这些恶心的限制以后,筛出所有符合的 ((a, b, c)) 数对:

    ((0, 5, 10), (0, 15, 0), (1, 6, 8), (2, 7, 6), (3, 8, 4), (4, 9, 2), (5, 0, 10), (6, 1, 8), (7, 2, 6), (8, 3, 4), (9, 4, 2), (10, 5, 0), (15, 0, 0))

    真tm好!


    对于一组 (a, b, c),考虑构造具体的方案。

    把每一步当作一个字符,形成的路径可以看做一个字符串如 (aaaaacccccccccc)

    具体的方案限制:

    • 每个 (a) 的前面的 (c) 的个数必须为偶数,即保证进行 (a) 操作时在内圈
    • 每个 (b) 的前面的 (c) 的个数必须为奇数,即保证进行 (b) 操作时在外圈。

    方案计算需要组合排列的知识。

    考虑先把 (c) 丢进去,构造方案地将 (a, b) 插入的方案。

    • 将每两个 (c) 化为一组,(?cc?cc?cc?) 。即每个 (?) 的位置可以插入 (0) 到无限多个 (a)。方案数即将 (a) 个插入这 (dfrac{c}{2} + 1) 个位置里,等价于 (x_1 + x_2 + ..+x_{frac{c}{2} + 1} = a) 非负整数解的方案数。用隔板法可知(老 生 常 谈)方案数为 (C_{a + frac{c}{2}}^frac{a - 1}{2})

    • 第一个 (c),后面每两个 (c) 化为一组,(c?cc?cc?c) 。即每个 (?) 的位置可以插入 (0) 到无限多个 (a)。方案数即将 (a) 个插入这 (dfrac{c}{2}) 个位置里,等价于 (x_1 + x_2 + ..+x_{frac{c}{2}} = b) 非负整数解的的方案数。用隔板法可知(老 生 常 谈)方案数为 (C_{b + frac{c}{2} - 1}^{frac{c}{2} - 1})

    故一种 (a, b, c) 三元组的贡献是 (C_{a + frac{c}{2}}^frac{c}{2} imes C_{b + frac{c}{2} - 1}^{frac{c}{2} - 1})。答案为所有贡献之和。

    注意特殊情况 (c = 0) 时,我们不会负数的组合数(无意义),不能用这个公式,横跳不到外圈:

    • 此时如果 (b > 0), 但是没地方放,当场去世。((0, 15, 0), (10, 5, 0))
    • ((0, 15, 0)) 显然方案为 (1)。狂走三圈。

    把刚才那一堆恶心的东西按照 (c) 排序应该会好算一点

    $ (4, 9, 2), (9, 4, 2), (3, 8, 4), (8, 3, 4), (2, 7, 6), (7, 2, 6), (1, 6, 8), (6, 1, 8) , (0, 5, 10), (5, 0, 10)$

    (Ans = 1 + C_5^1 imes C_{9}^0 + C_{10}^1 imes C_{4}^0 + C_{5}^2 imes C_{9}^1 + C_{10}^2 imes C_{4}^1+ C_5^3 imes C_{9}^2 + C_{10}^3 imes C_{4}^2 + C_{5}^4 imes C_{9}^3 + C_{10}^4 imes C_{4}^3 + C_5^5 imes C_{9}^4 + C_{10}^5 imes C_{4}^4)

    显然的,奇偶拆开,这是有规律的,但是我并没有找到,导致搞出来这么个破玩意:

    (Ans = 1 + C_5^1 imes C_{9}^0 + C_{5}^2 imes C_{9}^1 + C_5^3 imes C_{9}^2 + C_{5}^4 imes C_{9}^3 + C_5^5 imes C_{9}^4 + C_{10}^1 imes C_{4}^0 + C_{10}^2 imes C_{4}^1+ C_{10}^3 imes C_{4}^2 + C_{10}^4 imes C_{4}^3+ C_{10}^5 imes C_{4}^4)

    (= 1 + 5*1+10*9+10*36+5*84+1*126+10*1+45*4+120*6+210*4+252*1)

    (= 1 + 5 + 90 + 360 + 420+126+10+180+720+840+252)

    (= 3004)


    后续:

    这是人做的题吗???????????????????????????????????

    我再尝试一下能不能找到简单的组合意义。

    (Ans = 1 + C_5^1 imes C_{9}^0 + C_{5}^2 imes C_{9}^1 + C_5^3 imes C_{9}^2 + C_{5}^4 imes C_{9}^3 + C_5^5 imes C_{9}^4 + C_{10}^1 imes C_{4}^0 + C_{10}^2 imes C_{4}^1+ C_{10}^3 imes C_{4}^2 + C_{10}^4 imes C_{4}^3+ C_{10}^5 imes C_{4}^4)

    利用 (C_n^m = C_n^{n - m}) 将式子等价转化一下。

    (Ans = 1 + C_5^4 imes C_{9}^0 + C_{5}^3 imes C_{9}^1 + C_5^2 imes C_{9}^2 + C_{5}^1 imes C_{9}^3 + C_5^0 imes C_{9}^4 + C_{10}^1 imes C_{4}^4 + C_{10}^2 imes C_{4}^3+ C_{10}^3 imes C_{4}^2 + C_{10}^4 imes C_{4}^1+ C_{10}^5 imes C_{4}^0)

    (= 1 + sum_{a+b=4} C_5^a imes C_9^b + sum_{a + b = 5}C_4^a imes C_{10}^b)

    好吧还是什么都想不出来,佛了佛了。

    (大佬们应该能想出更为容易的组合意义表示,反正我是想不出来,目前能想到的就是这个枚举的是 (a = k+1)(k) 然后就想不到怎么分配了。

  • 相关阅读:
    c语言练习17——输入一行字符,分别统计出其中英文字母、空格、数字和其它字符的个数
    c语言练习16——输入两个正整数m和n,求其最大公约数和最小公倍数
    c语言练习15——条件运算符的嵌套
    c语言练习14——将一个正整数分解质因数
    CentOS下Cassandra集群搭建
    一台linux服务器挂载另外一台linux服务器文件系统
    zabbix分布式监控多网段的部署与实现
    CentOS安装MySQL详解
    vcenter 7.0 安装 vRealize Operations Manager
    Zabbix分布式部署详细
  • 原文地址:https://www.cnblogs.com/dmoransky/p/12680460.html
Copyright © 2011-2022 走看看