题目背景
上道题中,妖梦斩了一地的木棒,现在她想要将木棒拼起来。

题目描述
有 nnn 根木棒,现在从中选 444 根,想要组成一个正三角形,问有几种选法?

答案对 109+710^9+7109+7 取模。

输入格式
第一行一个整数 nnn 。第二行 nnn 个整数,第 iii 个整数 aia_iai​ 代表第 iii 根木棒的长度。

输出格式
一行一个整数代表答案。

输入输出样例
输入 #1

4
1 1 2 2

输出 #1

1

说明/提示
数据规模与约定

  • 对于 30%30\%30% 的数据,保证 n≤5×103n \le 5 \times 10^3n≤5×103。
  • 对于 100%100\%100% 的数据,保证 1≤n≤1051 \leq n \le 10^51≤n≤105,0≤ai≤5×1030 \le a_i \le 5 \times 10^30≤ai​≤5×103 。

解法 枚举+哈希表+组合

这道题有点意思。由于要用 444 根木棒组成正三角形,就必须要有两根木棒长度相等,剩下的一边,则由 222 根长度之和等于 前 222 根相等的木棒的长度 的木棒组成。

由于木棒长度 ai≤5000a_i \le 5000ai​≤5000 ,用 O(n2)O(n^2)O(n2) 的算法就能过,于是直接两重循环,暴力枚举上述两种木棒的长度,计算组合方案数并累加。

此处外层循环 cnt[]cnt[]cnt[] 数组,cnt[i]cnt[i]cnt[i] 为长度为 iii 的木棒的个数。要从 cnt[i]cnt[i]cnt[i] 根长度为 iii 的木棒中取出 222 根,即计算组合数 C(cnt[i],2)C(cnt[i], 2)C(cnt[i],2);内层循环中,要从剩余的木棒中取出两根长度之和为 iii 的木棒,令一根长度为 jjj ,另一根长度则为 i−ji - ji−j ,为避免重复计算,设 j≤i−jj \le i - jj≤i−j 。分类讨论:

  1. j==i−jj == i - jj==i−j 时,从长度为 jjj 的木棍中取出 222 根合为一条边, 方案数为 C(cnt[j],2)C(cnt[j], 2)C(cnt[j],2) ;
  2. j≠i−jj \ne i - jj​=i−j 时,从长度为 jjj 和长度为 i−ji- ji−j 的木棍中各取出一根,方案数为 C(cnt[j],1)×C(cnt[i−j],1)C(cnt[j], 1) \times C(cnt[i - j], 1)C(cnt[j],1)×C(cnt[i−j],1)

将所有外层方案数和内层方案数的乘积汇总,就是总的方案数。不过题目中有些地方描述不清楚, aia_iai​ 可以为 000 ,那么可以用三根长度一样的木棍加上一根长度为零的木棍,可以组成一个正三角形吗?三根长度为零的木棍,可以组成正三角形吗?尝试提交了几次,从AC代码中发现,这些情况是不允许的:

#include <bits/stdc++.h>
using namespace std;
const int maxn = 5e3 + 10, mod = 1e9 + 7;
int n, t, cnt[maxn], maxLen = 0, ans = 0;
bool flag = true; //所有长度的木棍都是唯一的
int C(int n, int k) { //n个数中选出k个数的组合数 return (k == 1 ? n : n * (n - 1) / 2) % mod; //k要么为1,要么为2
}
int main() {scanf("%d", &n);for (int i = 0; i < n; ++i) {scanf("%d", &t);++cnt[t];if (cnt[t] > 1) flag = false;maxLen = max(maxLen, t); //最长的木棍长度 }if (flag) { printf("0"); return 0; } //所有长度的木棍都是唯一的,无法组成正三角形for (int i = 2; i <= maxLen; ++i) { //枚举外层的两根长度为i的木棍组合 if (cnt[i] <= 1) continue; //枚举内层的一根木棍长度为j,另一根长度为i-jint times = C(cnt[i], 2) % mod; for (int j = 1; j <= i / 2; ++j) { //注意避免重复计算,令j<=i-j
//          if (j == 0 && cnt[j] >= 1 && cnt[i] >= 3)
//              ans += C(cnt[i], 3) * C(cnt[j], 1);if (j == i - j && cnt[j] >= 2)ans += times * C(cnt[j], 2) % mod;else if (j != i - j && cnt[j] >= 1 && cnt[i - j] >= 1) ans += times * C(cnt[j], 1) * C(cnt[i - j], 1) % mod;ans %= mod;}}printf("%d\n", ans);return 0;
}

洛谷 P3799 妖梦拼木棒【枚举/组合数学】相关推荐

  1. 【题解】【算法】- 洛谷 - P3799 妖梦拼木棒(组合数学)

    题目背景 上道题中,妖梦斩了一地的木棒,现在她想要将木棒拼起来. 题目描述 有 n 根木棒,现在从中选 4 根,想要组成一个正三角形,问有几种选法? 答案对 109 + 7 取模. 输入格式 第一行一 ...

  2. 洛谷[P3799 妖梦拼木棒] {暴力枚举} 奋斗的珂珂~

    洛谷[P3799 妖梦拼木棒] {暴力枚举} 题目背景 上道题中,妖梦斩了一地的木棒,现在她想要将木棒拼起来. 题目描述 有 n 根木棒,现在从中选 4 根,想要组成一个正三角形,问有几种选法? 答案 ...

  3. P3799 妖梦拼木棒——枚举+组合数学

    妖梦拼木棒 题目背景 上道题中,妖梦斩了一地的木棒,现在她想要将木棒拼起来. 题目描述 有 nnn 根木棒,现在从中选 444 根,想要组成一个正三角形,问有几种选法? 答案对 109+710^9+7 ...

  4. 洛谷-P3799 妖梦拼木棒

    题目背景 上道题中,妖梦斩了一地的木棒,现在她想要将木棒拼起来. 题目描述 有 nn 根木棒,现在从中选 44 根,想要组成一个正三角形,问有几种选法? 答案对 10^9+7109+7 取模. 输入格 ...

  5. 洛谷P3799 妖梦拼木棒

    题目链接 题目背景 上道题中,妖梦斩了一地的木棒,现在她想要将木棒拼起来. 题目描述 有n根木棒,现在从中选4根,想要组成一个正三角形,问有几种选法? 输入格式: 第一行一个整数n 第二行n个整数,a ...

  6. 洛谷P3799 妖梦拼木棒 题解

    //简单的思路:四根必有两根相同,所以咱们就先选两根组合成第三根,确定另外相同的两根的长度 //分为两种情况,一.预选两根相同长度.二.预选两根不同长度. //所有情况是预选*(确定的另外两根) #i ...

  7. 洛谷 P3799 妖梦拼木棒

    题目 这道题主要考组合数学,一开始我没注意数据范围,傻乎乎地模拟,结果复杂度爆炸10个TLE.这道题是算出来的. 思路是用一个栈把相同长度个数超过2的木棍用栈保存下来,同时用一个数组存下所有长度木棍的 ...

  8. [luogu P3799] 妖梦拼木棒

    [luogu P3799] 妖梦拼木棒 题目描述 解决过程 思路 代码 感想 题目描述 点击此处查看题目描述 解决过程 暴力不多阐述,很显然是无法AC的 解决此题需要用到组合数 思路 这道题要求拼成等 ...

  9. 洛谷 P3797 妖梦斩木棒 解题报告

    P3797 妖梦斩木棒 妖梦是住在白玉楼的半人半灵,拥有使用剑术程度的能力. 题目描述 有一天,妖梦正在练习剑术.地面上摆放了一支非常长的木棒,妖梦把它们切成了等长的\(n\)段.现在这个木棒可以看做 ...

最新文章

  1. 理解与使用Javascript中的回调函数
  2. Linux shell script 的语法汇总
  3. python深浅拷贝的底层理解_理解python中的深拷贝与浅拷贝
  4. 【转】使用Jmeter针对ActiveMQ JMS Point To Point压力测试
  5. 【OS学习笔记】三十七 保护模式十:中断和异常的处理与抢占式多任务对应的汇编代码----主引导扇区代码
  6. c form画直线_新手教程跟我一起画儿童裤子裁剪图
  7. 预测评价系统_「机器学习」一文读懂分类算法常用评价指标
  8. 【Spring笔记】Spring配置
  9. 【脑洞大开】假如BERT系列论文变成Commit History
  10. 研制埃博拉疫苗与科学家的奇思秒想
  11. ezd激光雕刻机软件使用笔记。
  12. 你不知道的华为交换机22个实用技巧
  13. 从Java程序员到架构师,从工程师到技术专家,迷茫之路
  14. Kotlin Flow详解
  15. 华为H3CNE认证题库、教材-热门下载帖汇总!
  16. P4839 P哥的桶 题解
  17. 如何做好App性能测试
  18. 对于Spring MCV的理解
  19. 和chatGPT聊了聊通信,答复如下:
  20. 【文献翻译】Epileptic Seizures Detection Using Deep Learning Techniques: A Review

热门文章

  1. 粘土人世纪开金手指不黑屏怎么弄
  2. 元宵节,祝福每个人快快乐乐,健健康康。
  3. win10 linux uef系统,win10 uefi 模式装archlinux
  4. [BZOJ 4244] 邮戳拉力赛
  5. 1153 - 三个整数
  6. 利用报表工具制作一张简单报表的主要流程
  7. Vue实现pptx在线预览
  8. html5微信拍照后自动刷新,html5 调用微信jssdk 没有调用相机,只显示最近的图片文件。...
  9. 阿里云ACP大数据分析师 | 笔记纪要
  10. 物流中转站---最短距离和