您的位置:首页 > 其它

2017.10.8 志愿者招募 失败总结

2017-10-08 15:24 204 查看
。这个题要是想用费用流写的话就太难了。

所以就要考虑统筹学的另一个工具--单纯形

实际上。很多网络流解决的都是线性规划的问题,,这些问题很多都可以用单纯形解

关于单纯形的学习资料网上很详细了。。这里就说一些代码实现上的小技巧

1、 换完基变量和非基变量,原来非基变量的位置直接赋值为基变量的值

2、操作的形式是    Xn+i  +  a1*X1  + a2* X2  + a3*X3   =    bi

带入的形式是   X1  =  bi/a1  -  Xn+i / a1  -  a2* X2 / a1  -  a3*X3 / a1

3、注意eps

4、这个题是对偶问题,,需要将原矩阵A 转置    b、c互换。。。。。。。

码:

#include<iostream>
#include<cstdio>
#include<cmath>
using namespace std;
#define eps 1e-7
double b[10005],a[10005][1005],c[1005],ans;
int n,m,i,j,x,y;
void pvt(int o,int wz)
{//cout<<endl<<o<<" "<<wz<<endl;
int i,j;
b[wz]/=a[wz][o];
for(i=1;i<=n;i++)
if(i!=o)
a[wz][i]/=a[wz][o];
a[wz][o]=1.0/a[wz][o];
for(i=1;i<=m;i++)
if(i!=wz&&fabs(a[i][o])>eps)
{
b[i]-=b[wz]*a[i][o];
// cout<<" "<<i<<" ";
for(j=1;j<=n;j++)
if(j!=o)
a[i][j]-=a[wz][j]*a[i][o];
a[i][o]=-a[i][o]*a[wz][o];// cout<<a[i][o]<<" ";
}//cout<<endl;
ans+=b[wz]*c[o];
// cout<<ans<<" ";
for(i=1;i<=n;i++)
if(i!=o)
c[i]-=c[o]*a[wz][i];
c[o]=-a[wz][o]*c[o];
}
void smp()
{
while(1)
{
int e,lin;
for(e=1;e<=n;e++)if(c[e]>eps)break;//找还没有解决的点
if(e==n+1)break;
// cout<<endl<<e<<endl;
double o=1e10;
for(i=1;i<=m;i++)
if(a[i][e]>eps&&(b[i]/a[i][e])<o)//找最小的 约束
{
o=(b[i]/a[i][e]);
lin=i;
}
// cout<<" "<<b[lin]<<" "<<a[lin][e];
pvt(e,lin);
}
}
int main()
{
scanf("%d%d",&n,&m);
for(i=1;i<=n;i++)
scanf("%lf",&c[i]);
for(i=1;i<=m;i++)
{
scanf("%d%d%lf",&x,&y,&b[i]);
for(j=x;j<=y;j++)
a[i][j]=1;
}
//for(i=1;i<=n;i++)printf("%.1lf ",c[i]);
smp();
printf("%.0lf",ans);
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: