先高斯消元求出每个点期望到达次数,再到边;
再利用排序不等式贪心求解;点1一开始就期望1;
要注意点n的特殊性,它原本期望为1,但每个点不能由它转移过去,
它的期望也与其它点无关,就让它为0以方便计算;
#include<bits/stdc++.h>
#define rep(i,k,n) for(int i=k;i<=n;i++)
using namespace std;
const int maxn=505,maxm=maxn*maxn;
typedef double db;
int g[maxn][maxn],d[maxn],n,m,s[maxm],t[maxm];
db a[maxn][maxn],p[maxn],ans[maxm],Ans=0.0;
void gauss(){
rep(i,1,n-1){db ok=0.0;int id=i;
rep(j,i,n-1)if(fabs(a[j][i])>ok){ok=fabs(a[j][i]);id=j;}
if(ok==0.0)continue;
if(id!=i)rep(j,1,n)swap(a[id][j],a[i][j]);
for(int j=n;j>=i;j--)
for(int k=1;k<n;k++)if(k!=i){
a[k][j]-=a[i][j]*a[k][i]/a[i][i];
}
}
rep(i,1,n-1)p[i]=a[i][n]/a[i][i];
}
int main(){//freopen("in.in","r",stdin);
int u,v;
scanf("%d%d",&n,&m);
rep(i,1,m){scanf("%d%d",&s[i],&t[i]);u=s[i];v=t[i];
g[u][v]++;g[v][u]++;d[u]++;d[v]++;}
rep(i,1,n-1)
rep(j,1,n-1){
if(i==j)a[i][j]=1.0;
else a[i][j]=-1.0*g[i][j]/d[j];
}
a[1][n]=1.0;
gauss();
rep(i,1,m){ans[i]=(p[s[i]]*1.0/d[s[i]])+(p[t[i]]*1.0/d[t[i]]);}
sort(ans+1,ans+1+m);
rep(i,1,m)Ans+=(m-i+1)*1.0*ans[i];
printf("%.3lf",Ans);
return 0;
}