程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> C++ >> C++入門知識 >> UVa 10755 - Garbage Heap 三維最大子矩陣問題轉化為1維..

UVa 10755 - Garbage Heap 三維最大子矩陣問題轉化為1維..

編輯:C++入門知識

  A上C(20,2)卡上下界...B上C(20,2)卡上下界...在C的方向上做一維的最大連續字串問題...這樣把3維的最大子矩陣問題就轉化為1維的了...

   預處理...sum[ x ] [ y ] [ z ] 代表在z這個二維平面上...(1,1)和(x,y)分別為對角坐標的矩陣的所有數之和....

 


Program:


[cpp]
//http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=1696  
#include<iostream>  
#include<stdio.h>  
#include<string.h>  
#include<cmath>  
#include<map>  
#include<algorithm>  
#define ll long long  
#define oo 2000000000  
using namespace std;     
int A,B,C; 
ll sum[22][22][22]; 
ll getsum(int As,int Ae,int Bs,int Be,int C) 

      return sum[Ae][Be][C]-sum[As-1][Be][C]-sum[Ae][Bs-1][C]+sum[As-1][Bs-1][C]; 

int main() 
{     
      int T,t,i,j,k,As,Ae,Bs,Be,Cs,Ce; 
      ll m,ans; 
      cin>>T; 
      for (t=1;t<=T;t++) 
      { 
            cin>>A>>B>>C; 
            memset(sum,0,sizeof(sum)); 
            for (i=1;i<=A;i++) 
              for (j=1;j<=B;j++) 
                for (k=1;k<=C;k++) 
                { 
                     cin>>sum[i][j][k]; 
                     sum[i][j][k]+=sum[i-1][j][k]+sum[i][j-1][k]-sum[i-1][j-1][k];  
                } 
            ans=-oo; 
            ans*=10000; 
            for (As=1;As<=A;As++) 
              for (Ae=As;Ae<=A;Ae++) 
                for (Bs=1;Bs<=B;Bs++) 
                  for (Be=Bs;Be<=B;Be++) 
                  { 
                         Cs=Ce=1; 
                         m=0; 
                         while (Ce<=C) 
                         { 
                               m+=getsum(As,Ae,Bs,Be,Ce); 
                               if (m>ans) ans=m; 
                               while (m<0 && Cs<=Ce) 
                               { 
                                     m-=getsum(As,Ae,Bs,Be,Cs); 
                                     Cs++; 
                                     if (Cs<=Ce && m>ans) ans=m; //保證至少一個矩陣  
                               } 
                               Ce++; 
                         } 
                  } 
            if (t!=1) cout<<endl; 
            cout<<ans<<endl; 
      } 
      return 0; 

/*
1
2 3 3
21 -39 4 -39 4 -44 1 -32 -25 -35 2 17 6 10 2 -12 -22 35 
 
ans 55
 
1
1 2 2
-38 40 21 -34 
 
ans 40
*/ 

//http://uva.onlinejudge.org/index.php?option=com_onlinejudge&Itemid=8&page=show_problem&problem=1696
#include<iostream>
#include<stdio.h>
#include<string.h>
#include<cmath>
#include<map>
#include<algorithm>
#define ll long long
#define oo 2000000000
using namespace std;   
int A,B,C;
ll sum[22][22][22];
ll getsum(int As,int Ae,int Bs,int Be,int C)
{
      return sum[Ae][Be][C]-sum[As-1][Be][C]-sum[Ae][Bs-1][C]+sum[As-1][Bs-1][C];
}
int main()
{   
      int T,t,i,j,k,As,Ae,Bs,Be,Cs,Ce;
      ll m,ans;
      cin>>T;
      for (t=1;t<=T;t++)
      {
            cin>>A>>B>>C;
            memset(sum,0,sizeof(sum));
            for (i=1;i<=A;i++)
              for (j=1;j<=B;j++)
                for (k=1;k<=C;k++)
                {
                     cin>>sum[i][j][k];
                     sum[i][j][k]+=sum[i-1][j][k]+sum[i][j-1][k]-sum[i-1][j-1][k];
                }
            ans=-oo;
            ans*=10000;
            for (As=1;As<=A;As++)
              for (Ae=As;Ae<=A;Ae++)
                for (Bs=1;Bs<=B;Bs++)
                  for (Be=Bs;Be<=B;Be++)
                  {
                         Cs=Ce=1;
                         m=0;
                         while (Ce<=C)
                         {
                               m+=getsum(As,Ae,Bs,Be,Ce);
                               if (m>ans) ans=m;
                               while (m<0 && Cs<=Ce)
                               {
                                     m-=getsum(As,Ae,Bs,Be,Cs);
                                     Cs++;
                                     if (Cs<=Ce && m>ans) ans=m; //保證至少一個矩陣
                               }
                               Ce++;
                         }
                  }
            if (t!=1) cout<<endl;
            cout<<ans<<endl;
      }
      return 0;
}
/*
1
2 3 3
21 -39 4 -39 4 -44 1 -32 -25 -35 2 17 6 10 2 -12 -22 35

ans 55

1
1 2 2
-38 40 21 -34

ans 40
*/


 

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved