求助 换教室 76pts
查看原帖
求助 换教室 76pts
112048
dfydn楼主2021/8/3 11:06
//f[i][j][0/1] 前i节课,已经更换j次,第i节课是否更换的期望最小 
#include<cstdio>
#include<iostream>
#include<cstring>
using namespace std;
typedef long long ll;
const int N=2005;
int tot; 
int n,m,v,e; 
int g[N][N];
int c[N],d[N];
double k[N];
double f[N][N][2];
void floyd(){
	for(int k=1;k<=v;k++){
		for(int i=1;i<=v;i++){
			for(int j=1;j<=v;j++){
				g[i][j]=min(g[i][j],g[i][k]+g[k][j]);
			}
		}
	}
}
int main(){
	memset(g,0x3f3f3f,sizeof(g));
	scanf("%d%d%d%d",&n,&m,&v,&e);
	for(int i=1;i<=n;i++) scanf("%d",&c[i]);
	for(int i=1;i<=n;i++) scanf("%d",&d[i]);
	for(int i=1;i<=n;i++) scanf("%lf",&k[i]);
	for(int i=1;i<=e;i++){
		int u,v,w;
		scanf("%d%d%d",&u,&v,&w);
		g[u][v]=g[v][u]=min(g[u][v],w);
	}
	floyd();
	for(int i=1;i<=v;i++) g[i][i]=g[0][i]=g[i][0]=0;
	for(int i=0;i<=n;i++)
	for(int j=0;j<=m;j++){
		f[i][j][0]=f[i][j][1]=1e17+5.0;
	}
	f[1][0][0]=f[1][1][1]=0;
	for(int i=2;i<=n;i++){
		f[i][0][0]=f[i-1][0][0]+g[c[i-1]][c[i]];
	}
	for(int i=2;i<=n;i++){
		for(int j=1;j<=min(i,m);j++){
			f[i][j][0]=min(f[i][j][0],min(f[i-1][j][1]+g[c[i-1]][c[i]]*(1-k[i-1])+k[i-1]*g[c[i]][d[i-1]],f[i-1][j][0]+g[c[i-1]][c[i]]));
			f[i][j][1]=min(f[i][j][1],min(f[i-1][j-1][1]+g[d[i-1]][d[i]]*k[i]*k[i-1]+g[d[i-1]][c[i]]*k[i-1]*(1-k[i])+g[c[i-1]][d[i]]*k[i]*(1-k[i-1]),f[i-1][j-1][0]+g[c[i-1]][d[i]]*k[i]+g[c[i-1]][c[i]]*(1-k[i])));
		}
	}
	double ans=1e17+7.0;
	for(int i=0;i<=m;i++){
		ans=min(ans,min(f[n][i][0],f[n][i][1]));
	}
	printf("%.2lf",ans);
	return 0;
}
2021/8/3 11:06
加载中...