思路:由于M相当之大,因此可以构造矩阵快速幂来求解
mat[i][j]表示第i个被子给第j个被子的水的百分比,如果k==0,则全给自己,mat[i][i]=1.0;
代码如下:
mat[i][j]表示第i个被子给第j个被子的水的百分比,如果k==0,则全给自己,mat[i][i]=1.0;
代码如下:
#include <iostream>
#include <fstream>
#include <cstring>
#include <cstdio>
#include <algorithm>
#include <iostream>
#include <vector>
#include <cmath>
#define MAX 31
using namespace std;
//矩阵乘法一定不要忘记将矩阵初始赋值为0
int n,k,t,m;
double data[21],avg,res;
struct node{
double kk[MAX][MAX];
}unit,a;
void init()
{
for(int i=1;i<=MAX;i++)
for(int j=1;j<=MAX;j++)
{
unit.kk[i][j]=(i==j);
a.kk[i][j]=0;
}
scanf("%d",&n);
for(int i=1;i<=n;i++)
scanf("%lf",&data[i]);
for(int i=1;i<=n;i++)
{
scanf("%d",&k);
if(k==0)
{
a.kk[i][i]=1.0;
continue;
}
avg=1.0/k;
for(int j=1;j<=k;j++)
{
scanf("%d",&t);
a.kk[i][t]=avg;
}
}
scanf("%d",&m);
}
node mul(node aa,node bb)
{
node cc;
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++)
{
cc.kk[i][j]=0;
for(int p=1;p<=n;p++)
cc.kk[i][j]=cc.kk[i][j]+(aa.kk[i][p]*bb.kk[p][j]);
}
return cc;
}
node pow(node aa,int exp)
{
node p=aa;
node q=unit;
while(exp)
{
if(exp&1)
q=mul(q,p);
exp/=2;
p=mul(p,p);
}
return q;
}
void cal()
{
node ans=pow(a,m);
for(int i=1;i<=n;i++)
{
res=0;
for(int j=1;j<=n;j++)
{
res+=(ans.kk[j][i]*data[j]);
}
if(i!=1)
printf(" ");
printf("%.2lf",res);
}
printf("\n");
}
int main()
{
int t;
scanf("%d",&t);
while(t--)
{
init();
cal();
}
return 0;
}