题意:黎明时,Venus为Psyche定下了第二个任务。她要渡过河,收集对岸绵羊身上的金羊毛。
那些绵羊狂野不驯,所以Psyche一直往地上丢树枝来把它们吓走。地上现在有 n根树枝,第 i 根树枝的长度是 ai
如果她丢的下一根树枝可以和某两根树枝形成三角形,绵羊就会被激怒而袭击她。
现在Psyche手中只有长度不小于 L 且不大于 R 的树枝。请你帮忙计算,她下一根可以丢多少种不同长度的树枝而不会把绵羊激怒呢?
个人感想:这道题有点坑…啊我本来的想法从区间中 总数(LR)-不合法(lr)=合法的区间.我不知道为什么我会想到 找最大的区间 并用总数减去,可是任意**两个区间并不一定相交!**所以在可选的区间中,某些位置的数也是合法的!!例如100 1000 10000, 假设我设为 b1,b2,b3,首先我对这堆数排序一下,可以发现
如果我们要求 不合法区间的个数必然要满足 a+b>L(可选)>b-a 其中(a< b)
而且
b3+b2>L>b3-b2;
b3+b1>L>b3-b1;前一个区间 必然包括后一个区间,为什么?
(b3+b2)-(b3+b1)>0;
(b3-b2)-(b3-b1)<0; 所以只要枚举相邻的两个长度即可.
分析:贪心.
代码:
/* Author:GavinjouElephant
* Title:
* Number:
* main meanning:
*
*
*
*/
//#define OUT
#include <iostream>
using namespace std;
#include <cstdio>
#include <cmath>
#include <cstring>
#include <algorithm>
#include <sstream>
#include <cctype>
#include <vector>
#include <set>
#include <cstdlib>
#include <map>
#include <queue>
//#include<initializer_list>
//#include <windows.h>
//#include <fstream>
//#include <conio.h>
#define MaxN 0x7fffffff
#define MinN -0x7fffffff
#define Clear(x) memset(x,0,sizeof(x))
const int INF=0x3f3f3f3f;
const int maxn=1e5+10;
int T;
int N;
long long L,R;
long long mL,mR;
long long x[maxn];
int main()
{
#ifdef OUT
freopen("coco.txt","r",stdin);
freopen("lala.txt","w",stdout);
#endif
scanf("%d",&T);
while(T--)
{
cin>>N>>L>>R;
for(int i=0;i<N;i++)
{
cin>>x[i];
}
sort(x,x+N);
long long ans=0;
for(int i=N-1;i>=1;i--)
{
long long l=x[i]-x[i-1]+1;
long long r=x[i]+x[i-1]-1;
if(l>R||r<L)continue;
if(R>r)ans+=(R-r);
R=l-1;
if(L>R)break;
}
if(R>=L)ans+=(R-L+1);
cout<<ans<<endl;
}
return 0;
}