本文主要是介绍2020年12月3日提高组 C 毛毛的三角,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
文章目录
R e s u l t Result Result
H y p e r l i n k Hyperlink Hyperlink
https://www.luogu.com.cn/problem/U142634
D e s c r i p t i o n Description Description
有 n n n种木棍,第 i i i种木棍的长度为 2 i − 1 2^{i-1} 2i−1,它有 a i a_i ai根
问用这些木棍最多能同时拼出多少个三角形
数据范围: n ≤ 3 × 1 0 5 , a i ≤ 1 0 9 n\leq 3\times 10^5,a_i\leq 10^9 n≤3×105,ai≤109
S o l u t i o n Solution Solution
显然一个三角形三边长必然是 ( 2 i , 2 j , 2 j ) i ≤ j (2^i,2^j,2^j)i\leq j (2i,2j,2j)i≤j的形式
显然大部分情况下1,2,2的情况是最优的,当然也有可能是1,1,1这种情况
贪心的先考虑前者,再考虑后者就好了
具体地, c a n p p canpp canpp表示现在可以(1,2,2)匹配的数量, n e e d need need表示前面需要匹配的
假设第 i i i种木棍有 x x x根,那么 c a n p p = m i n ( ⌊ x 2 ⌋ , n e e d ) canpp=min(\lfloor \frac x 2\rfloor,need) canpp=min(⌊2x⌋,need),然后去匹配,接着看如果木棍有剩余,不小于三根的话让其自我匹配就好了
时间复杂度: O ( n ) O(n) O(n)
C o d e Code Code
#include<cctype>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define LL long long
#define N 300010
using namespace std;int n,x,need,canpp;
LL res;
inline LL read()
{char c;LL d=1,f=0;while(c=getchar(),!isdigit(c)) if(c=='-') d=-1;f=(f<<3)+(f<<1)+c-48;while(c=getchar(),isdigit(c)) f=(f<<3)+(f<<1)+c-48;return d*f;
}
signed main()
{n=read();for(register int i=1;i<=n;i++) {x=read();canpp=min(x/2,need);need-=canpp;res+=canpp;x-=canpp*2;res+=x/3;need+=x%3;}printf("%lld",res);
}
这篇关于2020年12月3日提高组 C 毛毛的三角的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!