HDU - 2859 Phalanx(动态规划/哈希表)
生活随笔
收集整理的這篇文章主要介紹了
HDU - 2859 Phalanx(动态规划/哈希表)
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
題目鏈接:點擊查看
題目大意:給定一個整數n,然后給出一個n*n的方陣,求方陣中最大的對稱子方陣(對稱指的是以右上角至左下角為對角線)
分析:這個題網上有個一般做法,相當于一個動態規劃的小模擬,時間復雜度為,這里不再贅述,一會直接上代碼。
然后還有一個方法,是那天講題的時候,鑫爺以非同常人的腦回路提出的,可以先用打一個哈希表,然后再遍歷每一個點進行
判斷,如果判斷相等則直接更新,如果不相等則可以二分查找最長的相等子序列,這樣時間復雜度就下降到了logn了,提交的
時候比一般方法快了十倍還多,不得感嘆真的tql。
直接上代碼吧:
一般做法:
#include<iostream> #include<cstdio> #include<string> #include<cstring> #include<algorithm> #include<stack> #include<queue> #include<map> #include<sstream> #include<cmath> using namespace std;typedef long long LL;const int inf=0x3f3f3f3f;const int N=1e3+100;char maze[N][N];int dp[N][N];int main() { // freopen("input.txt","r",stdin);int n;while(scanf("%d",&n)!=EOF&&n){for(int i=0;i<n;i++)scanf("%s",maze+i);fill(dp[0],dp[0]+N*N,1);int ans=1;for(int i=1;i<n;i++)for(int j=0;j<n;j++){int x=i;int y=j;while(maze[x][j]==maze[i][y]){x--;y++;if(x<0||y>=n)break;}x=i-x;//所記錄的最長相等子序列的長度if(x>dp[i-1][j+1]){dp[i][j]=dp[i-1][j+1]+1;}elsedp[i][j]=x;ans=max(dp[i][j],ans);}cout<<ans<<endl;}return 0; }哈希表+二分:
#include<iostream> #include<cstdio> #include<string> #include<cstring> #include<algorithm> #include<stack> #include<queue> #include<map> #include<sstream> #include<cmath> using namespace std;typedef long long LL;typedef unsigned long long ULL;const int inf=0x3f3f3f3f;const int N=1e3+100;ULL p[N],hash_1[N][N],hash_2[N][N];char maze[N][N];int dp[N][N];void hash_(int n) {for(int i=1;i<=n;i++)for(int j=1;j<=n;j++){hash_1[i][j]=hash_1[i][j-1]*131+(maze[i][j]-'a'+1);}for(int j=1;j<=n;j++)for(int i=n;i>=1;i--){hash_2[i][j]=hash_2[i+1][j]*131+(maze[i][j]-'a'+1);} }void initp() {p[0]=1;for(int i=1;i<N;i++)p[i]=p[i-1]*131; }void init(int n) {memset(maze,0,sizeof(maze));for(int i=1;i<=n;i++)for(int j=1;j<=n;j++)dp[i][j]=1;memset(hash_1,0,sizeof(hash_1));memset(hash_2,0,sizeof(hash_2)); }int main() { // freopen("input.txt","r",stdin);int n;initp();while(scanf("%d",&n)!=EOF&&n){init(n);for(int i=1;i<=n;i++)scanf("%s",maze[i]+1);hash_(n);int mmax=1;for(int i=2;i<=n;i++)for(int j=n-1;j>=1;j--){int k=dp[i-1][j+1];ULL a=hash_1[i][j+k]-hash_1[i][j-1]*p[k+1];ULL b=hash_2[i-k][j]-hash_2[i+1][j]*p[k+1];if(a==b)dp[i][j]=k+1;else{int l=1,r=k;int ans=0;while(l<=r){int mid=(l+r)/2;ULL a=hash_1[i][j+mid]-hash_1[i][j-1]*p[mid+1];ULL b=hash_2[i-mid][j]-hash_2[i+1][j]*p[mid+1];if(a==b){ans=mid;l=mid+1;}else{r=mid-1;} }dp[i][j]=ans+1;}mmax=max(mmax,dp[i][j]);}cout<<mmax<<endl;}return 0; }?
超強干貨來襲 云風專訪:近40年碼齡,通宵達旦的技術人生總結
以上是生活随笔為你收集整理的HDU - 2859 Phalanx(动态规划/哈希表)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: POJ - 3259 Wormholes
- 下一篇: HYSBZ - 1026 windy数(