思路:
将期望dp[x]看成自变量,那么递推式就可以看成方程组,用高斯消元求方程组的解就能求解出期望值
高斯消元求解的过程也是期望逆推的过程,注意边界情况的常数项,是6/d,不是1
代码:
#pragma GCC optimize(2)#pragma GCC optimize(3)#pragma GCC optimize(4)#includeusing namespace std;#define y1 y11#define fi first#define se second#define pi acos(-1.0)#define LL long long//#define mp make_pair#define pb emplace_back#define ls rt<<1, l, m#define rs rt<<1|1, m+1, r#define ULL unsigned LL#define pll pair #define pli pair #define pii pair #define piii pair #define pdd pair #define mem(a, b) memset(a, b, sizeof(a))#define debug(x) cerr << #x << " = " << x << "\n";#define fio ios::sync_with_stdio(false);cin.tie(0);cout.tie(0);//headconst int N = 105;double A[N][N];void Gauss(int n) { for(int i = 0; i < n; i ++) { int r = i; for(int j = i + 1; j < n; j ++) if(fabs(A[j][i]) > fabs(A[r][i])) r = j; if(r != i) for(int j = 0; j <= n; j ++) swap(A[r][j], A[i][j]); for(int j = n; j >= i; j --) { for(int k = i + 1; k < n; k ++) A[k][j] -= A[k][i] / A[i][i] * A[i][j]; } } for(int i = n - 1; i >= 0; i --) { for(int j = i + 1; j < n; j ++) A[i][n] -= A[j][n] * A[i][j]; A[i][n] /= A[i][i]; }}int T, n, a, b, to[105];int main() { scanf("%d", &T); for(int cs = 1; cs <= T; ++cs) { scanf("%d", &n); for (int i = 1; i <= 100; ++i) to[i] = 0; for (int i = 1; i <= n; ++i) scanf("%d %d", &a, &b), to[a] = b; for (int i = 0; i <= 100; ++i) for (int j = 0; j <= 100; ++j) A[i][j] = 0; for (int i = 1; i <= 100; ++i) { A[i-1][i-1] = 1; if(to[i]) { A[i-1][to[i]-1] = -1; } else { int x = min(6, 100-i); for (int j = 1; j <= x; ++j) { A[i-1][i+j-1] = -1.0/x; } if(i < 100) A[i-1][100] = 6.0/x; } } Gauss(100); printf("Case %d: %.10f\n", cs, A[0][100]); } return 0;}