金字塔

 

金字塔 

Jaguar 国王在一场战役大胜后决定建造一个金字塔,一方面作为纪念战争胜利的纪念碑,同时亦用作埋葬在战斗中阵亡将士们的墓地。该金字塔将建在战场的所在地,有一个ab行的矩形底部。在金字塔的底层内将有一个较小的cd行的矩形墓室,用来存放阵亡将士们的遗体以及他们所用过的武器。

国王的建筑师将该战场分为mn行小方格的网格。每个小方格的高度用一个整数表示。

金字塔及其内部的墓室均应覆盖网格的完整的小方格,而且其边必须与战场的边平行。金字塔内墓室小方格的高度必须保持原有的高度不变,但金字塔底部的其余地面则需要平整,平整的方法是将高度较高的小方格内的砂土移到较低的小方格内,这样一来,金字塔底部的最后高度将是底部所覆盖的所有小方格(墓室小方格除外)高度的平均值。建筑师有权选择墓室在金字塔内的位置,但墓室四周要有至少一小方格厚度的墙围绕。

建筑师希望在战场上找到一块最佳的位置来建造该金字塔及其内部的墓室,使得对于给定大小的金字塔,其底部的高度尽可能高。

图中所示是一个战场的例子,每个小方格内的整数表示该格所处区域内的高度。灰色部份表示金字塔的底部,灰色部份所包围的白色部份则表示墓室的位置。该图给出了一个最佳位置。

任务 

对于给定尺寸的战场、金字塔和墓室大小以及战场上所有小方格的高度,请编写一程序找出建造金字塔及其墓室的最佳位置,使得金字塔底部的高度为最高。

限制条件

3 ≤ m ≤ 1000

3 ≤ n ≤ 1000

3 ≤ a m

3 ≤ b n

1 c a – 2

1 d b – 2

所有的高度值都是1-100之间的整数。

输入 

你的程序必须从文件 pyramid.in 中读入所需数据,其格式如下:

输出

 

你的程序必须将结果数据输出到pyramid.out的文件中。

 ================================================

只可过这么多..若要过完必须2个单调队列优化

===========================================

var
  m,n,a,b,c,d,num:longint;
  map,f:array[0..1001,0..1001]of longint;
procedure init;
begin
  assign(input,'pyramid.in');
  assign(output,'pyramid.out');
  reset(input); rewrite(output);
end;

procedure terminate;
begin
  close(input); close(output);
  halt;
end;

procedure main;
var
  i,j,k,l:longint;
  ans:extended;
  t1,t2:longint;
  x1,y1,x2,y2:longint;
begin
  readln(m,n,a,b,c,d);
  num:=a*b-c*d;
  for i:=1 to n do
    for j:=1 to m do
      read(map[i,j]);
      
  fillchar(f,sizeof(f),0);
  for i:=n downto 1 do
    for j:=m downto 1 do
      f[i,j]:=f[i+1,j]+f[i,j+1]+map[i,j]-f[i+1,j+1];
      //表示以[n,m]与[i,j]构成的矩形大小
      
  ans:=0;
  for i:=n-b+1 downto 1 do
    for j:=m-a+1 downto 1 do
      begin
        t1:=f[i,j]-f[i+b,j]-f[i,j+a]+f[i+b,j+a];
        t2:=maxlongint;
        for k:=i+b-d-1 downto i+1 do
          for l:=j+a-c-1 downto j+1 do
            if t2>f[k,l]-f[k+d,l]-f[k,l+c]+f[k+d,l+c] then
              begin
                t2:=f[k,l]-f[k+d,l]-f[k,l+c]+f[k+d,l+c];
                if ans<extended(t1-t2)/num then
                  begin
                    ans:=extended(t1-t2)/num;
                    x1:=i; y1:=j;
                    x2:=k; y2:=l;
                  end;
              end;
      end;
      
  writeln(y1,' ',x1);
  writeln(y2,' ',x2);
end;

begin
  init;
  main;
  terminate;
end.


 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值