hdu1506
给你一些直方图,问包含的最大矩形面积.
思路:枚举每一个直方,寻找左右大于等于它的边界,然后求max. 注意优化技巧
int main(){
int n;
while(cin>>n && n){
int a[n+2];
for(int i=1;i<=n;i++)cin>>a[i];
int l[n+2],r[n+2];
l[1]=1;r[n]=n;//左右边界
for(int i=n-1;i>=1;i--){ //注意顺序,这样可以把前面算过的不用再算一遍
int t=i;
while(a[t+1] >= a[i] && t+1<=n)t=r[t+1];//优化,不用一个一个找
r[i]=t;
}
for(int i=2;i<=n;i++){
int t=i;
while(a[t-1] >= a[i] && t-1>=1)t=l[t-1];
l[i]=t;
}
ll ans=0;
for(int i=1;i<=n;i++){
ans=max(ans,(ll)a[i]*(r[i]-l[i]+1));
}
cout<<ans<<endl;
}
return 0;
}
hdu1505
是上一题的加强版,在一个平面里,有一片空地,有几处障碍物,输出平面里最大的矩形.
思路:用dp[i][j]表示第i行第j列以上的高度,然后和上面那一题一样每一行计算一下max,
const int MAXN=1005;
int c,n,m,dp[MAXN][MAXN];
char mp[MAXN][MAXN];
void init(){
cin>>n>>m;
for(int i=1;i<=n;i++){
for(int j=1;j<=m;j++){
cin>>mp[i][j];
}
}
for(int i=1;i<m;i++)dp[0][i]=0;
}
void solve(){
ll maxn=0,ans=0;
for(int w=1;w<=n;w++){
for(int i=1;i<=m;i++){
dp[w][i]=dp[w-1][i];
if(mp[w][i] == 'F')dp[w][i]++;
else if(mp[w][i] == 'R')dp[w][i]=0;
}
int l[m+2],r[m+2];
l[1]=1;r[m]=m;
for(int i=m-1;i>=1;i--){
int t=i;
while(dp[w][t+1] >= dp[w][i] && t+1<=m)t=r[t+1];
r[i]=t;
}
for(int i=2;i<=n;i++){
int t=i;
while(dp[w][t-1] >= dp[w][i] && t-1>=1)t=l[t-1];
l[i]=t;
}
ll ans=0;
for(int i=1;i<=n;i++){
ans=max(ans,(ll)dp[w][i]*(r[i]-l[i]+1));
}
if(ans>maxn)maxn=ans;
}
cout<<maxn*3<<endl;
}
int main(){
int c;cin>>c;
while(c--){
init();
solve();
}
return 0;
}
hdu1069
给你一些长方体,每个知道长宽高,数量无限,将它堆起来求max,要求下面的长宽要比上面的长宽大,不然不稳.
const int MAXN=200;
const int MOD=998244353;
int t=0;
struct node{
int x,y,z;
}p[MAXN];
bool cmp(node a,node b){
if(a.x>b.x)return true;
return false;
}
void init(int a,int b,int c){
t++;
p[t].x=a;
p[t].y=b;
p[t].z=c;
}
int x,y,z;
int c;
int dp[MAXN];
int main(){
SIS;
int n;int c=1;
while(cin>>n && n){
t=0;
for(int i=0;i<n;i++){
cin>>x>>y>>z;//长宽高都放一个试试
init(x,y,z);
init(x,z,y);
init(y,x,z);
init(y,z,x);
init(z,x,y);
init(z,y,x);
}
sort(p+1,p+t+1,cmp);
memset(dp,0,sizeof(dp));
dp[1]=p[1].z;
for(int i=2;i<=t;i++){
dp[i]=p[i].z;
for(int j=i-1;j>=1;j--){//把当前物体放在前面能放的地方
if(p[i].x<p[j].x && p[i].y<p[j].y)
dp[i]=max(dp[i],dp[j]+p[i].z);
}
}
int maxn=0;
for(int i=1;i<=t;i++){
maxn=max(maxn,dp[i]);
}
printf("Case %d: maximum height = %d\n",c,maxn);
c++;
}
}
!! hdu1176
用mp[i][j]表示在第i秒在j点掉落的个数
用dp[i][j]表示在到第i秒走到j点最大的收获
int mp[100005][15];
int dp[100005][15];
int c;
int main(){
SIS;
while(~scanf("%d",&c) && c){
int a,b;
memset(mp,0,sizeof(mp));
memset(dp,0,sizeof(dp));
int maxt=0;
for(int i=1;i<=c;i++){
scanf("%d%d",&a,&b);
a++;
mp[b][a]++;
maxt=max(maxt,b);
}
for(int j=1;j<=11;j++)dp[maxt][j]=mp[maxt][j];
for(int i=maxt-1;i>=0;i--){
for(int j=1;j<=11;j++){
dp[i][j]=max(dp[i+1][j-1],
max(dp[i+1][j],dp[i+1][j+1]))+mp[i][j];
}
}
printf("%d\n",dp[0][6]);
}
return 0;
}