您的位置:首页 > 其它

hdu 5135 状态压缩dp

2015-03-01 19:52 381 查看
题意是给出最对12条边你     问最大可组成三角形面积是多大 (可有多个三角形)   典型的状态压缩  (最多12条边)    

思路:
先暴力枚举所有可能三角形的面积   然后再根据状态压缩来做    最多可组成n/3个三角形  对每个三角形都记录三边或(运算)    和面积    然后判断进行合并  (根据且运算)   就行了

#include<stdio.h>
#include<string.h>
#include<cmath>
#include<iostream>
using namespace std;

double dp[1<<14];
double max(double a,double b)
{
return a>b?a:b;
}
struct node
{
int pp;
double area;
}cont[1<<14];
int main()
{
int n,i,j,k;
int num[15];
double S;
while(~scanf("%d",&n),n)
{
for(i=1;i<=n;i++)
scanf("%d",&num[i]);
memset(dp,0,sizeof(dp));
int t=0;
S=0;
for(i=1;i<=n;i++)
for(j=i+1;j<=n;j++)
{
for(k=j+1;k<=n;k++)
{
if(num[i]+num[j]>num[k]&&num[i]+num[k]>num[j]&&num[j]+num[k]>num[i])
{
double p=1.0*(num[i]+num[j]+num[k])/2;
t++;
double s=sqrt(p*(p-num[i])*(p-num[j])*(p-num[k]));
cont[t].pp=(1<<i)|(1<<j)|(1<<k);
dp[(1<<i)|(1<<j)|(1<<k)]=cont[t].area=s;
}
}
}
for(i=1;i<(1<<(n+1));i++)
{
for(j=1;j<=t;j++)
{
if((i&cont[j].pp)==0)
{
dp[i|cont[j].pp]=max(dp[i|cont[j].pp],dp[i]+cont[j].area);
if(dp[i|cont[j].pp]>S) S=dp[i|cont[j].pp];
}
}
}
printf("%.2lf\n",S);
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  压缩