#1042 : 跑马圈地(思维+枚举)

时间限制: 10000ms
单点时限: 1000ms
内存限制: 256MB

描述

一觉醒来,小Hi穿越回了古代!由于破敌有功,大汗赏赐小Hi可以在敌人的草原上跑马圈地:一天之内骑马围住的草原以后就是小Hi的牧场。但是令小Hi头疼的是,敌人的草原上有一块臭水塘。小Hi不能骑马走进臭水塘里,并且即使小Hi的骑马路径围住了臭水塘,小Hi的牛马也不能在臭水塘里放牧。

为了更科学地圈地,小Hi对这个问题进行了简化和抽象:(1)敌人的草原是一块n×m的方格矩阵,(2)骑马的路径是沿着方格边缘的一段封闭折线,(3)臭水塘是矩阵中的一块矩形,(4)骑马的路径周长不超过L。小Hi想知道自己最大能圈住多大面积的草原(臭水塘的面积不计入在内)。

如图所示:图1是一条合法的路径;图2也是一条合法的路径,但是圈住的草原面积为0;图3不是合法的路径,因为没有封闭;图4也不是合法的路径,因为穿过了水塘。

输入

第一行3个整数:n, m, L (1 <= n, m <= 100, 1 <= L <= 400)

第二行4个整数:l, r, t, b (0 <= l < r <= m, 0 <= t < b <= n)表示水塘的左、右、上、下边界坐标。

输出

小Hi最大能圈住的面积

样例输入
4 4 8
1 3 1 3
样例输出
3

分析:这道题不太能想到,就是把复杂问题简单化,可以看出,有很多种覆盖的情况,无非是不覆盖,覆盖一个角,两个,全覆盖。当覆盖两个角的时候可以看出是缺边的。这样必须让面积再次缩小,否则周长不够,可以不用考虑。而覆盖一个角的时候周长是可以沿着水塘一遍的,正好周长够了,无非是面积小了点。全覆盖的话就是显然的了。

难点在于思路有了如何去实现。

这里用到了一个转化的思想,就是水塘在草原里实际上是有所侧重的(位置),而为了统一,我们把所有水塘偏向的情况都统一放在右下角的方位处,然后枚举就可以了。具体代码如下:

#include<iostream>
#include<stdio.h>
using namespace std;
int main()
{
    int n,m,L,l,r,t,b,l1,r1,t1,b1;
    int ans=0;
    scanf("%d%d%d",&n,&m,&L);
    scanf("%d%d%d%d",&l,&r,&t,&b);

    if(l+r<=m&&t+b<=n)//这样说明偏向哪侧。自拿实例验证
    {
        l1=m-r;
        r1=m-l;
        t1=n-b;
        b1=n-t;
    }
    else if(l+r<=m&&t+b>n)
    {
        l1=m-r;
        r1=m-l;
        t1=t;
        b1=b;
    }
    else if(l+r>m&&t+b<=n)
    {
        l1=l;
        r1=r;
        t1=n-b;
        b1=n-t;
    }//剩下的一种情况本身就已经是右下角了
    for(int i=0;i<=L/2&&i<=n;i++)//依次枚举
    {
        for(int j=0;j<=L/2&&j<=m&&i+j<=L/2;j++)
        {
            if(i<=t1||j<=l1)//这种情况就是不经过水塘的
                ans=max(ans,i*j);
            if(i>t1&&i<=b1&&j>l1&&j<=r1)//正好经过水塘一个角
                ans=max(ans,i*j-(i-t1)*(j-l1));
            if(i>b1&&j>r1)//全覆盖
                ans=max(ans,i*j-(b1-t1)*(r1-l1));
        }
    }
    printf("%d",ans);
    return 0;

}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值