洛谷 U96762 小R与三角形 题解
U96762 小R与三角形
题目描述
小 R 所在的小镇有 n 个村落,这 n 个村落分布在一个圆周上,这些村落之间两两有直达的小路,小路可能相交,但不存在三条路交于一点。现在小 R 正好放暑假了,每天都在村落间游荡。一天,他发现可以从一个非村落的点出发,在不经过村落的情况下经过三条小路再回到这个点。于是他很好奇,一共有多少个这样的回路呢?
输入格式
第一行一个正整数 n,含义如上。
输出格式
第一行一个正整数,表示回路的个数
输入输出样例
输入 #1
6
输出 #1
1
输入 #2
20
输出 #2
38760
说明/提示
对于 50%的数据,有 n<=20。 对于 100%的数据,有 n<=100。
【思路】
先分析一下提议,求在圆上n个点互相连接之后构成的顶点不是这n个点中任意一个点的三角形有多少个。
看起来很麻烦的样子对不对?一想,哇,这么多边花里胡哨的怎么搞好啊?
其实很简单,样例已经看穿了一切(手动滑稽)
第一个样例6个点可以构成1个这样的三角形,所以可以类比出来任意6个点都可以构成这么一个三角形,所以n个点能够构成多少个这样的三角形,就是在n个里面取出6个的组合数。
怎么样是不是很简单的亚子!!
【暴力求组合数】
组合数的公式是这样的:
\]
直接暴力算就可以了,但是有一个很难受的地方就是这道题没有模数,所以这样暴力求阶乘很容易爆long long
所以只能拿50分
【完整代码】
#include<iostream>
#include<cstdio>
#define int long long
using namespace std;
int read()
{
int sum = 0,fg = 1;
char c = getchar();
while(c < '0' || c > '9')
{
if(c == '-')fg = -1;
c = getchar();
}
while(c >= '0' && c <= '9')
{
sum = sum * 10 + c - '0';
c = getchar();
}
return sum * fg;
}
int jc(int x)
{
int ans = 1;
for(register int i = 1;i <= x;++ i)
ans *= i;
return ans;
}
int C(int n,int m)
{
return jc(n) / (jc(m) * (jc(n - m)));
}
signed main()
{
int n = read();
cout << C(n,6) << endl;
}
递归求组合数
阶乘求组合数爆掉的原因是因为超出了long long,因为\(C_n^m\)本身没有超出long long的范围,只是在除出正确的结果之前先爆掉了long long,所以可以用递归求组合数的方法吼!因为这样是直接求\(C_n^m\)的值,所以不会爆掉。
虽然不会爆long long了,但是,很可怕的一件事出现了,那就是超时了,因为这个递归求组合数复杂度太高了,会超时,只能拿70分。
【完整代码】
#include<iostream>
#include<cstdio>
using namespace std;
int read()
{
int sum = 0,fg = 1;
char c = getchar();
while(c < '0' || c > '9'){if(c == '-')fg = -1;c = getchar();}
while(c >= '0' && c <= '9'){sum = sum * 10 + c - '0';c = getchar();}
return sum * fg;
}
int C(int n,int m)
{
if(n == m)return 1;
if(m == 0)return 1;
return C(n - 1,m) + C(n - 1,m - 1);
}
int main()
{
int n = read();
if(n <= 5)
{
cout << 0 << endl;
return 0;
}
cout << C(n,6) << endl;
}
但是,超时也是有原因的——重复计算多次组合数
这就是100*100,一共才10000中组合数,一个只计算一遍都不会超时,所以出现超时情况只能是重复计算,所以记忆化就用上啦!
轻轻松松A掉,跑的飞快。
【完整代码】
#include<iostream>
#include<cstdio>
using namespace std;
const int Max = 101;
int c[Max][Max];
int read()
{
int sum = 0,fg = 1;
char c = getchar();
while(c < '0' || c > '9'){if(c == '-')fg = -1;c = getchar();}
while(c >= '0' && c <= '9'){sum = sum * 10 + c - '0';c = getchar();}
return sum * fg;
}
int C(int n,int m)
{
if(c[n][m] != 0)return c[n][m];
if(n == m)return c[n][m] = 1;
if(m == 0)return c[n][m] = 1;
return c[n][m] = C(n - 1,m) + C(n - 1,m - 1);
}
int main()
{
int n = read();
if(n <= 5)
{
cout << 0 << endl;
return 0;
}
cout << C(n,6) << endl;
}
【阶乘公式改进法】
但是我a某人觉得记忆化不够优美,所以要改进这个阶乘公式!
\]
因为m是一定的,而且阶乘暴力求解只在n大的时候才会爆,为什么要提到这个呢?原因就是n!是1到n乘起来,除以了1到m乘起来的数和1到(n-m)乘起来的数,上面的1到n乘起来的数可以和下面某一个越掉一部分,比如和1到m乘起来的数一约就变为了m+1到n乘起来的数。
但是这两个怎么选择呢?就用到了刚才提到的,在n大的时候才会爆掉,所以和1到(n-m)乘起来的数约掉显然是更优的,毕竟m!阶乘就是个720太小了,不如前者更优。
所以式子就可以化为
\]
轻轻松松!
【完整代码】
#include<iostream>
#include<cstdio>
#define int long long
using namespace std;
const int Max = 101;
int c[Max][Max];
int read()
{
int sum = 0,fg = 1;
char c = getchar();
while(c < '0' || c > '9'){if(c == '-')fg = -1;c = getchar();}
while(c >= '0' && c <= '9'){sum = sum * 10 + c - '0';c = getchar();}
return sum * fg;
}
int C(int n,int m)
{
if(c[n][m] != 0)return c[n][m];
if(n == m)return c[n][m] = 1;
if(m == 0)return c[n][m] = 1;
return c[n][m] = C(n - 1,m) + C(n - 1,m - 1);
}
signed main()
{
int n = read();
if(n <= 5)
{
cout << 0 << endl;
return 0;
}
int ans = 1;
for(register int i = n - 5;i <= n;++ i)
ans *= i;
cout << ans / 720 << endl;
return 0;
}
洛谷 U96762 小R与三角形 题解的更多相关文章
- 洛谷 U2878 小R的分数比赛(fraction)
题目提供者 2015c07 标签 数论(数学相关) 高精度 难度 尚无评定 通过/提交 0/29 提交该题 记录 题目背景 P5难度系数:★★★☆☆ 小R再次挑战你. 这次的挑战又会是什么呢? 题目描 ...
- 洛谷 P1993 小K的农场 题解
每日一题 day55 打卡 Analysis 这是我们一次考试的T1,但我忘了差分约束系统怎么写了,所以就直接输出Yes混了60分 首先转化题目: 1:表示农场 a 比农场 b 至少多种植了 c 个单 ...
- 洛谷P1854 花店橱窗布置 分析+题解代码
洛谷P1854 花店橱窗布置 分析+题解代码 蒟蒻的第一道提高+/省选-,纪念一下. 题目描述: 某花店现有F束花,每一束花的品种都不一样,同时至少有同样数量的花瓶,被按顺序摆成一行,花瓶的位置是固定 ...
- 洛谷1373 小a和uim之大逃离
洛谷1373 小a和uim之大逃离 本题地址:http://www.luogu.org/problem/show?pid=1373 题目背景 小a和uim来到雨林中探险.突然一阵北风吹来,一片乌云从北 ...
- 莫队 [洛谷2709] 小B的询问[洛谷1903]【模板】分块/带修改莫队(数颜色)
莫队--------一个优雅的暴力 莫队是一个可以在O(n√n)内求出绝大部分无修改的离线的区间问题的答案(只要问题满足转移是O(1)的)即你已知区间[l,r]的解,能在O(1)的时间内求出[l-1, ...
- 2017提高组D1T1 洛谷P3951 小凯的疑惑
洛谷P3951 小凯的疑惑 原题 题目描述 小凯手中有两种面值的金币,两种面值均为正整数且彼此互素.每种金币小凯都有 无数个.在不找零的情况下,仅凭这两种金币,有些物品他是无法准确支付的.现在小 凯想 ...
- 洛谷P1120 小木棍
洛谷1120 小木棍 题目描述 乔治有一些同样长的小木棍,他把这些木棍随意砍成几段,直到每段的长都不超过50. 现在,他想把小木棍拼接成原来的样子,但是却忘记了自己开始时有多少根木棍和它们的长 ...
- 洛谷 P4430 小猴打架
洛谷 P4430 小猴打架 题目描述 一开始森林里面有N只互不相识的小猴子,它们经常打架,但打架的双方都必须不是好朋友.每次打完架后,打架的双方以及它们的好朋友就会互相认识,成为好朋友.经过N-1次打 ...
- HAOI2006 (洛谷P2341)受欢迎的牛 题解
HAOI2006 (洛谷P2341)受欢迎的牛 题解 题目描述 友情链接原题 每头奶牛都梦想成为牛棚里的明星.被所有奶牛喜欢的奶牛就是一头明星奶牛.所有奶 牛都是自恋狂,每头奶牛总是喜欢自己的.奶牛之 ...
随机推荐
- Prometheus 运维监控
Prometheus 运维监控 1.Prometheus 介绍详解 2.Prometheus 安装部署 3.Prometheus 配置文件详解 4.Prometheus PromSQL 常用资源 5. ...
- MonkeyDev安装--逆向开发
MonkeyDev是原有iOS OpenDev的升级,非越狱插件的开发集成神器! 可以使用Xcode开发CaptainHook Tweak.Logos Tweak 和 Command-line Too ...
- 目标检测算法之R-CNN和SPPNet原理
一.R-CNN的原理 R-CNN的全称是Region-CNN,它可以说是第一个将深度学习应用到目标检测上的算法.后面将要学习的Fast R-CNN.Faster R-CNN全部都是建立在R-CNN基础 ...
- 前端学习:HTML的学习总结
html简介 1 html是什么:超文本标记语言 超文本:文字/图片/音频/视频 标签/标记:<body></body> 怎么做:使用标签来创建网页 2 HTML的用途:是用来 ...
- JAVA学习之开发环境配置
JAVA SDK 下载地址:https://www.oracle.com/technetwork/java/javase/downloads/jdk8-downloads-2133151.html 版 ...
- C#工具类MySqlHelper,基于MySql.Data.MySqlClient封装
源码: using System; using System.Collections.Generic; using System.Linq; using System.Text; using Syst ...
- 小程序上传图片功能 uploadFile:fail Read error:ssl=0xa738d808:I/O error during system call,Connection reset by peer
由于纯网页上传图片小程序会闪退,就采用了小程序原生的上传功能wx.uploadfile 处理流程: 1.网页需要跳转到小程序 需要引用 <script src='https://res.wx.q ...
- Delphi - 10进制16进制相互转换
10进制转16进制 使用IntToHex可以实现十进制到十六进制的转换,注意这里的参数有两个,第一个表示需要被转换的10进制数,第二个表示转换后用几位来显示16进制数. 代码如下: function ...
- PIE SDK影像快速拼接
1.算法功能简介 快速拼接是对若干幅互为邻接的遥感数字图像拼在一起,构成一幅整体影像的技术过程.PIE支持快速拼接算法功能的执行,下面对快速拼接算法功能进行介绍. 2.算法功能实现说明 2.1 实现步 ...
- JS 将数值取整为10的倍数
问题描述: 将数值处理为 10 的倍数,并支持向上或者向下取整 如将 2345 可以处理为 2300 | 2400 | 3000 | 2000 解决方案: /** * 将数字取整为10的倍数 * @p ...