装备购买 线性基+贪心

装备购买

Solution:

贪心+线性基。

由于线性基能够表出的线性空间和原数表出的线性空间相同,

所以只需要在高斯消元求线性基的过程中贪心选取价格最低的行(向量)即可。

Code:

#include<cmath>
#include<string>
#include<cstdio>
#include<cstring>
#include<algorithm>
#define RG register
#define IL inline
#define LL long long
#define LDB long double
using namespace std;

IL int gi() {
	char ch=getchar(); RG int x=0,w=0;
	while(ch<'0'||ch>'9') {if (ch=='-') w=1;ch=getchar();}
	while(ch>='0'&&ch<='9') x=x*10+(ch^48),ch=getchar();
	return w?-x:x;
}

const int N=510;
const LDB eps=1e-6;

LDB a[N][N];
int n,m,cnt,ans,c[N];

IL void Gauss_Jordan() {
	RG int i,j,k,l;
	for(i=1;i<=n;++i) {
		for(j=cnt+1,l=0;j<=n;++j)
			if(fabs(a[j][i])>eps&&(c[j]<c[l]||!l)) l=j;
		if(!l) continue;
		++cnt,ans+=c[l];
		if(l!=i) {
			swap(c[l],c[cnt]);
			for(j=i;j<=m;++j) swap(a[l][j],a[cnt][j]);
		}
		for(j=i+1;j<=m;++j) a[cnt][j]/=a[cnt][i];
		a[cnt][cnt]=1.0;
		for(j=1;j<=n;++j) {
			if(j==i||fabs(a[j][i])<=eps) continue;
			RG LDB res=a[j][i]/a[cnt][i];
			for(k=i;k<=m;++k) a[j][k]-=res*a[cnt][k];
		}	
	}
}

int main()
{
	RG int i,j;
	n=gi(),m=gi();
	for(i=1;i<=n;++i)
		for(j=1;j<=m;++j) scanf("%Lf",&a[i][j]);
	for(i=1;i<=n;++i) c[i]=gi();
	Gauss_Jordan();
	printf("%d %d\n",cnt,ans);	
	return 0;
}

posted @ 2019-04-04 17:14  薄荷凉了夏  阅读(182)  评论(0编辑  收藏  举报