单一栈-棋盘制作
单调栈-棋盘制作
program as;
var
a,b : array[0..2000,0..2000]of longint;
c : array[0..2000,1..2]of longint;
n,m,i,j,l,cfx,zfx : longint;
function min(a,b : longint):longint;
begin
if a>b then exit(b);
exit(a);
end;
procedure chuli(l,r,j:longint);
begin
for l:=l to r do
begin
if c[l,1] *(j-c[l,2])>cfx then
cfx:=c[l,1] *(j-c[l,2]);
if ((j-c[l,2])>zfx)and(j-c[l,2]>zfx) then
zfx:=min(c[l,1],j-c[l,2]);
end;
end;
begin
readln(n,m);
for i:=1 to n do
begin
for j:=1 to m do
begin
read(a[i,j]);
if (i=1)or(a[i,j]=a[i-1,j]) then
begin
b[i,j]:=1;
end
else
begin
b[i,j]:=b[i-1,j]+1;
end;
end;
readln;
end;
for i:=1 to n do
begin
l:=1;
c[1,1]:=b[i,1];
c[1,2]:=1;
for j:=2 to m do
begin
if a[i,j]<>a[i,j-1] then
begin
while c[l,1]>b[i,j] do
begin
chuli(l,l,j);
if c[l-1,1]<b[i,j] then
begin
c[l,1]:=b[i,j];
break;
end
else
begin
dec(l);
end;
end;
if c[l,1]<b[i,j] then
begin
inc(l);
c[l,1]:=b[i,j];
c[l,2]:=j;
end;
end
else
begin
chuli(1,l,j);
l:=1;
c[l,1]:=b[i,j];
c[l,2]:=j;
end;
end;
j:=m+1;
chuli(1,l,j);
end;
writeln(zfx*zfx);
writeln(cfx);
end.
这道题刚做的时候觉得比队列简单可是,做了才知道不好处理(队列要控制两个指针,而栈就控制一个),最应该注意的是出栈时的处理,分为两中出栈一种是全出,另一种是a[n]到a[n-1],a[n]到a[n-2],a[n]到a[n-3].......a[n]到a[1],
最后还要考虑到全出栈的情况。