题意:
给你两个二进制串a,b。你可以将a中的任意一位进行反转(0->1, 1->0)。问将a变成b操作次数的期望值是多少。
思路:
自己是看了幻想家协会会长: 讲解视频才会做的这道题,讲的很透彻。
首先我们先求出a和b其实有多少个位置不同用cnt来记录。如果cnt=0直接输出0就是了。
那么我们每一次操作无非就两种结果cnt+1, cnt-1。那么就此我们可以列出一个关于期望的式子f(x),他的意思就是有x个位置不同变成相同的期望值。
f
(
x
)
=
1
+
x
n
f
(
x
−
1
)
+
n
−
x
n
f
(
n
+
1
)
f(x) = 1+\frac{x}{n}f(x-1)+\frac{n-x}{n}f(n+1)
f(x)=1+nxf(x−1)+nn−xf(n+1)
式子的讲解:首先你一定会操作一次,操作过后的效果无非就两种,第一你把相同的改成不同也就是
n
−
x
n
f
(
n
+
1
)
\frac{n-x}{n}f(n+1)
nn−xf(n+1)从相同中的去选,第二你把不同的改成相同的
x
n
f
(
x
−
1
)
\frac{x}{n}f(x-1)
nxf(x−1)从不同中的去选。
那么我们就此往下递推:
f
(
n
)
=
f
(
n
−
1
)
+
1
<
1
>
.
f
(
n
−
1
)
=
1
+
n
−
1
n
f
(
n
−
2
)
+
1
n
f
(
n
)
<
2
>
f(n) = f(n-1)+1 <1>\\ . \\ f(n-1) = 1+\frac{n-1}{n}f(n-2)+\frac{1}{n}f(n)<2>\\
f(n)=f(n−1)+1<1>.f(n−1)=1+nn−1f(n−2)+n1f(n)<2>
将1式带入2式,我们就可以得出:
f
(
n
−
1
)
=
A
∗
f
(
n
−
2
)
+
B
.
.
f
(
k
)
=
A
k
∗
f
(
k
−
1
)
+
B
k
f(n-1) = A*f(n-2)+B \\ .\\ .\\ f(k) = A_k*f(k-1)+B_k
f(n−1)=A∗f(n−2)+B..f(k)=Ak∗f(k−1)+Bk
由此我们已知退出f(1),f(0)是等与0的那么
f
(
1
)
=
B
1
f(1) = B_1
f(1)=B1,我们按照上式已知往下推我们就可以推出
B
1
B _1
B1
然后再有f(1)推出f(cnt),求出答案;
代码:
#include<bits/stdc++.h>
#define IOS ios::sync_with_stdio(false);cin.tie(nullptr)
#define int long long
#define endl "\n"
using namespace std;
const int N = 2e6 + 10, mod = 998244353;
int ksm(int a, int b)
{
int ans = 1;
while(b)
{
if(b & 1) ans = ans*a %mod;
a = a * a % mod;
b >>= 1;
}
return ans;
}
int n, m, k, _;
char s1[N], s2[N];
int arr[N], brr[N];
void solve()
{
cin >> n >> s1+1 >> s2+1;
int cnt = 0;
for(int i = 1; i <= n; i ++)
if(s1[i] != s2[i]) cnt++;
if(cnt == 0)
{
cout << 0 << endl;
return;
}
arr[n] = brr[n] = 1;
for(int i = n-1; i >= 1; i --)
{
int t = ksm((n - (n-i) * arr[i+1]) % mod + mod, mod-2);
arr[i] = i * t % mod;
brr[i] = (n+ (n-i) * brr[i+1]) % mod * t % mod;
//cout << t << " " << arr[i] << " " << brr[i] << endl;
}
int ans = brr[1];
for(int i = 2; i <= cnt; i ++) ans = (ans * arr[i] + brr[i]) % mod;
cout << ans << endl;
}
signed main()
{
IOS;
cin >> _;
while(_--)
solve();
return 0;
}
补充
这里对于arr[i], brr[i]的推导代码进行讲述一下,自己最开始也很疑惑。
∵
f
(
k
)
=
A
k
∗
f
(
k
−
1
)
+
B
k
;
.
f
(
n
−
i
)
=
1
+
i
n
∗
f
(
n
−
i
−
1
)
+
n
−
i
n
∗
f
(
n
)
;
.
f
(
n
−
i
)
=
1
+
i
n
∗
f
(
n
−
i
−
1
)
+
n
−
i
n
∗
(
A
i
∗
f
(
i
−
1
)
+
B
i
)
;
.
f
(
n
−
i
)
=
1
+
i
n
∗
f
(
n
−
i
−
1
)
+
n
−
i
n
∗
A
i
∗
f
(
i
−
1
)
+
n
−
i
n
∗
B
i
;
.
(
1
−
n
−
i
n
∗
A
i
)
f
(
n
−
i
)
=
i
n
∗
f
(
n
−
i
−
1
)
+
n
−
i
n
∗
B
i
+
1
;
.
n
−
(
n
−
i
)
∗
A
i
n
∗
f
(
n
−
i
)
=
i
n
∗
f
(
n
−
i
−
1
)
+
(
n
−
i
)
B
i
+
n
n
;
.
f
(
n
−
i
)
=
n
n
−
(
n
−
i
)
∗
A
i
∗
(
i
n
∗
f
(
n
−
i
−
1
)
+
(
n
−
i
)
B
i
+
n
n
)
;
.
f
(
n
−
i
)
=
1
n
−
(
n
−
i
)
∗
A
i
∗
(
i
∗
f
(
n
−
i
−
1
)
+
(
n
−
i
)
B
i
+
n
)
;
\because f(k) = A_k*f(k-1)+B_k; \\ .\\ f(n-i) = 1+\frac{i}{n} * f(n-i-1) + \frac{n-i}{n}*f(n);\\ .\\ f(n-i) = 1+\frac{i}{n} * f(n-i-1) + \frac{n-i}{n}*( A_{i}*f(i-1)+B_{i});\\ .\\ f(n-i) = 1+\frac{i}{n}*f(n-i-1) + \frac{n-i}{n}* A_{i}*f(i-1)+ \frac{n-i}{n}*B_{i};\\ .\\ (1-\frac{n-i}{n}*A_i)f(n-i) = \frac{i}{n}*f(n-i-1)+\frac{n-i}{n}*B_i+1;\\ .\\ \frac{n-(n-i)*A_i}{n}*f(n-i) = \frac{i}{n}*f(n-i-1)+\frac{(n-i)B_i+n}{n};\\ .\\ f(n-i) = \frac{n}{n-(n-i)*A_i}*(\frac{i}{n}*f(n-i-1)+\frac{(n-i)B_i+n}{n});\\ .\\ f(n-i) = \frac{1}{n-(n-i)*A_i}*(i*f(n-i-1)+(n-i)B_i+n);
∵f(k)=Ak∗f(k−1)+Bk;.f(n−i)=1+ni∗f(n−i−1)+nn−i∗f(n);.f(n−i)=1+ni∗f(n−i−1)+nn−i∗(Ai∗f(i−1)+Bi);.f(n−i)=1+ni∗f(n−i−1)+nn−i∗Ai∗f(i−1)+nn−i∗Bi;.(1−nn−i∗Ai)f(n−i)=ni∗f(n−i−1)+nn−i∗Bi+1;.nn−(n−i)∗Ai∗f(n−i)=ni∗f(n−i−1)+n(n−i)Bi+n;.f(n−i)=n−(n−i)∗Ain∗(ni∗f(n−i−1)+n(n−i)Bi+n);.f(n−i)=n−(n−i)∗Ai1∗(i∗f(n−i−1)+(n−i)Bi+n);
代码中的t =
1
n
−
(
n
−
i
)
∗
A
i
\frac{1}{n-(n-i)*A_i}
n−(n−i)∗Ai1就是这么来的。