Lights inside 3D Grid
You are given a 3D grid, which has dimensions X, Y and Z. Each of the X x Y x Z cells contains a light. Initially all lights are off. You will have K turns. In each of the K turns,
1.You select a cell A randomly from the grid,
2.You select a cell B randomly from the grid and
3.Toggle the states of all the bulbs bounded by cell A and cell B, i.e. make all the ON lights OFF and make all the OFF lights ON which are bounded by A and B. To be clear, consider cell A is (x1, y1, z1) and cell B is (x2, y2, z2). Then you have to toggle all the bulbs in grid cell (x, y, z) where min(x1, x2) ≤ x ≤ max(x1, x2), min(y1, y2) ≤ y ≤ max(y1, y2) and min(z1, z2) ≤ z ≤ max(z1, z2).
Your task is to find the expected number of lights to be ON after K turns.
Input
Input starts with an integer T (≤ 50), denoting the number of test cases.
Each case starts with a line containing four integers X, Y, Z (1 ≤ X, Y, Z ≤ 100) and K (0 ≤ K ≤ 10000).
Output
For each case, print the case number and the expected number of lights that are ON after K turns. Errors less than 10-6 will be ignored.
Sample Input
5
1 2 3 5
1 1 1 1
1 2 3 0
2 3 4 1
2 3 4 2
Sample Output
Case 1: 2.9998713992
Case 2: 1
Case 3: 0
Case 4: 6.375
Case 5: 9.09765625
题意
给出一个XYZ的立方体,每个节点都有一个灯,开始处于关闭状态,随机选择两个点作为小立方体的对角线端点,将小立方体内的灯全部翻转,问操作k次后,亮的灯的个数的期望
题解
数学期望
首先直接推递推式想不到,只能考虑每个点的贡献了,首先每个点翻转的概率可以得到(自己一开始推得有些瑕疵,看了博客才改正的),因为这个点翻转,选的两点的坐标就一定在该点坐标的两侧或者就是自身,也就是以横坐标为例,只有选的两点的横坐标
x
i
,
x
j
(
x
i
<
=
x
j
)
x_i,x_j(x_i<=x_j)
xi,xj(xi<=xj)满足
x
i
≤
x
h
e
r
e
≤
x
j
x_i\leq x_{here}\leq x_j
xi≤xhere≤xj时,用选的点都在一边求x概率为
p
x
=
1
−
(
X
−
x
)
2
+
(
x
−
1
)
2
X
2
p_x=1-\cfrac{(X-x)^2+(x-1)^2}{X^2}
px=1−X2(X−x)2+(x−1)2,且
y
,
z
y,z
y,z都满足该关系时才能翻转,即翻转概率
p
=
p
x
p
y
p
z
p=p_xp_yp_z
p=pxpypz
然后就是考虑每个点的灯k次操作后想要处于亮的状态,那个该点一定是翻转了奇数次。
所以令
i
i
i为小于等于
k
k
k的奇数,则有
C
k
1
p
1
(
1
−
p
)
k
−
1
+
C
k
3
p
3
(
1
−
p
)
k
−
3
+
⋯
+
C
k
i
p
i
(
1
−
p
)
k
−
i
+
⋯
C_k^1p^1(1-p)^{k-1}+C_k^3p^3(1-p)^{k-3}+\cdots+C_k^ip^i(1-p)^{k-i}+\cdots
Ck1p1(1−p)k−1+Ck3p3(1−p)k−3+⋯+Ckipi(1−p)k−i+⋯
然后我就卡在这里了。。。完全忘记了奇数项的组合数公式,看了博客才继续推下去
公式
(
a
+
b
)
n
=
C
n
0
a
0
b
n
+
C
n
1
a
1
b
n
−
1
+
⋯
+
C
n
n
a
n
b
0
(
(
−
a
)
+
b
)
n
=
C
n
0
a
0
b
n
−
C
n
1
a
1
b
n
−
1
+
⋯
+
(
−
)
C
n
n
a
n
b
0
\begin{aligned}(a+b)^n&=C_n^0a^0b^n+C_n^1a^1b^{n-1}+\cdots+C_n^na^nb^0\\ ((-a)+b)^n&=C_n^0a^0b^n-C_n^1a^1b^{n-1}+\cdots+(-)C_n^na^nb^0 \end{aligned}
(a+b)n((−a)+b)n=Cn0a0bn+Cn1a1bn−1+⋯+Cnnanb0=Cn0a0bn−Cn1a1bn−1+⋯+(−)Cnnanb0
做差得2倍奇数项:
(
a
+
b
)
n
−
(
(
−
a
)
+
b
)
n
=
2
C
n
1
a
1
b
n
−
1
+
2
C
n
3
a
3
b
n
−
3
⋯
(a+b)^n-((-a)+b)^n=2C_n^1a^1b^{n-1}+2C_n^3a^3b^{n-3}\cdots
(a+b)n−((−a)+b)n=2Cn1a1bn−1+2Cn3a3bn−3⋯
有该公式得本题:
1
−
(
1
−
2
p
)
k
2
=
C
k
1
p
1
(
1
−
p
)
k
−
1
+
C
k
3
p
3
(
1
−
p
)
k
−
3
+
⋯
+
C
k
i
p
i
(
1
−
p
)
k
−
i
+
⋯
\cfrac{1-(1-2p)^k}{2}=C_k^1p^1(1-p)^{k-1}+C_k^3p^3(1-p)^{k-3}+\cdots+C_k^ip^i(1-p)^{k-i}+\cdots
21−(1−2p)k=Ck1p1(1−p)k−1+Ck3p3(1−p)k−3+⋯+Ckipi(1−p)k−i+⋯
然后期望将每点的概率求和即可
代码
#include <bits/stdc++.h>
using namespace std;
#define me(x,Y) Z(x,y,sizeof x)
#define MIN(x,y) x < y ? x : y
#define MAX(x,y) x > y ? x : y
typedef long long ll;
typedef unsigned long long ull;
const int maxn = 1e5+10;
const int INF = 0x3f3f3f3f;
const int MOD = 1e9+7;
const double eps = 1e-09;
const double PI = acos(-1.0);
double P(int x,int i){
return (1.0-(1.0*(i-1)*(i-1)+1.0*(x-i)*(x-i))/(x*x));
}
int main(){
int t,ca=1;cin>>t;
while(t--){
int X,Y,Z,k;
cin>>X>>Y>>Z>>k;
double ans=0;
for(int x=1; x <= X; ++x){
for(int y = 1; y <= Y; ++y){
for(int z = 1; z <= Z; ++z){
double p=P(X,x)*P(Y,y)*P(Z,z);
ans += (1-pow(1-2*p,k))/2;
}
}
}
printf("Case %d: %.10f\n",ca++,ans);
}
return 0;
}