Permutation Bo
Time Limit: 2000/1000 MS (Java/Others) Memory Limit: 131072/131072 K (Java/Others)Total Submission(s): 0 Accepted Submission(s): 0
Special Judge
Problem Description
There are two sequences
h1∼hn
and
c1∼cn
.
h1∼hn
is a permutation of
1∼n
. particularly,
h0=hn+1=0
.
We define the expression [condition] is 1 when condition is True,is 0 when condition is False.
Define the function f(h)=∑ni=1ci[hi>hi−1 and hi>hi+1]
Bo have gotten the value of c1∼cn , and he wants to know the expected value of f(h) .
We define the expression [condition] is 1 when condition is True,is 0 when condition is False.
Define the function f(h)=∑ni=1ci[hi>hi−1 and hi>hi+1]
Bo have gotten the value of c1∼cn , and he wants to know the expected value of f(h) .
Input
This problem has multi test cases(no more than
12
).
For each test case, the first line contains a non-negative integer n(1≤n≤1000) , second line contains n non-negative integer ci(0≤ci≤1000) .
For each test case, the first line contains a non-negative integer n(1≤n≤1000) , second line contains n non-negative integer ci(0≤ci≤1000) .
Output
For each test cases print a decimal - the expectation of
f(h)
.
If the absolute error between your answer and the standard answer is no more than 10−4 , your solution will be accepted.
If the absolute error between your answer and the standard answer is no more than 10−4 , your solution will be accepted.
Sample Input
4 3 2 4 5 5 3 5 99 32 12
Sample Output
6.000000 52.833333
题意:对于每个排列h 求出f(h)的期望;
一开始看到排列组合就有点怕,仔细分析以后发现:
C中:第一个数和最后一个数加到和中的次数是一样的 例如第一组数据 对于第一个数 3 ;如果H[1]=2 1*2种组合 如 2 1 * *
H[1]=3 则有2*2中组合 如 3 1 * * 或者 3 2 * *
H[1]=4 则有3*2种组合 如 4 1 * * 或者 4 2 * * 或者 4 3 * *
那么对于k 则有 (k-1)*A[n-2][n-2]种 第一位为k,第二位从小于k的数中选择,其余的数任意排列
而中间数值被加入总和则是: 第i为 放入k 则i-1位和i+1位从小于k的数中选择两个放入,其余的数任意排列 即 A[k][2]*A[n-3][n-3]
按照上面计算总和是会数据溢出的 但是因为要求的是期望 所以最后还要除掉A[n][n]
即 第一位和最后一位的贡献为 ANS1=sum(1,n-1)/(n*(n-1))
中间位则是 ANS2=sum(A[2][2],A[n-1][2])/(n*(n-1)*(n-2))
这样整个c序列则可以分为两个部分 ANS1*sum(c[1],c[n])+ANS2*sum(c[2]~c[n-1])
#include<cstdio>
#include<iostream>
#include<cstring>
#include<queue>
#include<cmath>
#define ll long long
using namespace std;
ll A[1010][3];
int main()
{
A[1][2]=0;
for(int i=2;i<=1000;i++)
{
A[i][2]=(i*(i-1))+A[i-1][2];
}
int n;
while(~scanf("%d",&n))
{
ll sum1=0,sum2=0;
for(int i=0;i<n;i++)
{
int a;
scanf("%d",&a);
if(i==0||i==n-1)
{
sum1+=a;
}
else sum2+=a;
}
if(n==1)
{
printf("%.5lf\n",(double)sum1);
}
else if(n==2)
{
printf("%.5lf\n",(double)sum1/2);
}
else
{
ll num=(n-1)*n/2;
//cout<<num<<" "<<sum1<<endl;
sum1*=num;
double ans=(double)sum1/(n*(n-1));
num=A[n-1][2];
//cout<<num<<" "<<sum2<<endl;
sum2*=num;
ans+=(double)sum2/(n*(n-1)*(n-2));
printf("%.5lf\n",ans);
}
}
}
f(h)=∑ni=1ci[hi>hi−1 and hi hi>hi−1 and hi>hi+1