bzoj1057: [zjoi2007]棋盤製作
西洋棋是世界上最古老的博弈遊戲之一,和中國的圍棋、象棋以及日本的將棋同享盛名。
據說西洋棋起源於易經的思想,棋盤是乙個8*8大小的黑白相間的方陣,對應八八六十四卦,黑白對應陰陽。
而我們的主人公小q,正是西洋棋的狂熱愛好者。
作為乙個頂尖高手,他已不滿足於普通的棋盤與規則,於是他跟他的好朋友小w決定將棋盤擴大以適應他們的新規則。
小q找到了一張由n*m個正方形的格仔組成的矩形紙片,每個格仔被塗有黑白兩種顏色之一。
小q想在這種紙中裁減一部分作為新棋盤,當然,他希望這個棋盤盡可能的大。
不過小q還沒有決定是找乙個正方形的棋盤還是乙個矩形的棋盤(當然,不管哪種,棋盤必須都黑白相間,即相鄰的格仔不同色),所以他希望可以找到最大的正方形棋盤面積和最大的矩形棋盤面積,從而決定哪個更好一些。
於是小q找到了即將參加全國資訊學競賽的你,你能幫助他麼?
第一行包含兩個整數n和m,分別表示矩形紙片的長和寬。
接下來的n行包含乙個n * m的01矩陣,表示這張矩形紙片的顏色(0表示白色,1表示黑色)。
包含兩行,每行包含乙個整數。第一行為可以找到的最大正方形棋盤的面積,第二行為可以找到的最大矩形棋盤的面積(注意正方形和矩形是可以相交或者包含的)。
3 31 0 1
0 1 0
1 0 046
n, m ≤ 2000
據說這個題可以單調棧做但是本蒟蒻不會啊。。。
最近$dp$寫多了腦子都瓦特了。。。
設:$left[i][j]$:代表從$(i,j)$能到達的最左位置
$right[i][j]$:代表從$(i,j)$能到達的最右位置
$up[i][j]$:代表從$(i,j)$向上擴充套件最長長度
因為$up[i][j]$的定義,$up$陣列代表向上擴充套件最長長度,所以需要考慮上一層的情況。
於是狀態轉移方程:
$$left[i][j]=\max\left\{}left[i][j]\\left[i-1][j]\end\right.$$
$$right[i][j]=\min\left\{}right[i][j]\\right[i-1][j]\end\right.$$
然後分正方形和長方形兩種情況即可。
據說這個方法叫懸線法。。。
定義:用一條線(橫豎貌似都行)左右移動直到不滿足約束條件或者到達邊界。
附**:
#include#include#include#define maxn 2010using namespace std;
int n,m,ans1=0,ans2=0;
int chess[maxn][maxn],left[maxn][maxn],right[maxn][maxn],up[maxn][maxn];
inline int read()
while(c>='0'&&c<='9')
return date*w;
}void work()
int x=right[i][j]-left[i][j]+1,y=min(x,up[i][j]);
ans1=max(ans1,y*y);
ans2=max(ans2,x*up[i][j]);
} printf("%d\n%d\n",ans1,ans2);
}void init()
for(int i=1;i<=n;i++)
}int main()
BZOJ1057 ZJOI2007 棋盤製作
西洋棋是世界上最古老的博弈遊戲之一,和中國的圍棋 象棋以及日本的將棋同享盛名。據說西洋棋起源 於易經的思想,棋盤是乙個8 8大小的黑白相間的方陣,對應八八六十四卦,黑白對應陰陽。而我們的主人公小q,正是西洋棋的狂熱愛好者。作為乙個頂尖高手,他已不滿足於普通的棋盤與規則,於是他跟他的好朋友小w決定 將...
bzoj1057 ZJOI2007 棋盤製作
傳送門 我們可以先用o nm 時間求出向左向右擴充套件的最大距離 然後o nm 列舉下端點位置 在矩形下面的邊上 計算出當高最高時的寬度,相乘後取max 正方形同理,只要取高度和寬度的min就行了。uses math var hei,a,x,y,le,ri array 0.2005,0.2005 o...
BZOJ1057 ZJOI2007 棋盤製作
西洋棋是世界上最古老的博弈遊戲之一,和中國的圍棋 象棋以及日本的將棋同享盛名。據說西洋棋起源 於易經的思想,棋盤是乙個8 8大小的黑白相間的方陣,對應八八六十四卦,黑白對應陰陽。而我們的主人公小q,正是西洋棋的狂熱愛好者。作為乙個頂尖高手,他已不滿足於普通的棋盤與規則,於是他跟他的好朋友小w決定 將...