Cod sursa(job #8496)

Utilizator moga_florianFlorian MOGA moga_florian Data 24 ianuarie 2007 21:20:49
Problema Elimin Scor 10
Compilator cpp Status done
Runda Arhiva de probleme Marime 3.35 kb
using namespace std;
#include<fstream>
#include<stdio.h>

int a[550][17],sl[550],sc[17];
int st[7300],nst;
char el[550],ec[550];
int lin[7300],col[7300];

void intersc(int i,int j)
{
st[i]^=st[j];
st[j]^=st[i];
st[i]^=st[j];

lin[i]^=lin[j];
lin[j]^=lin[i];
lin[i]^=lin[j];

col[i]^=col[j];
col[j]^=col[i];
col[i]^=col[j];     
}
     

int main()
{
FILE *fin=fopen("elimin.in","r"),
     *fout=fopen("elimin.out","w");
     
int m,n,r,c,inv=0,i,j;
fscanf(fin,"%d%d%d%d",&m,&n,&r,&c);

if(m<n)
  {
  inv=1;
  
  m^=n;
  n^=m;
  m^=n;
  
  r^=c;
  c^=r;
  r^=c;     
  
  for(j=1;j<=n;j++)
    for(i=1;i<=m;i++)
       fscanf(fin,"%d",&a[i][j]);
  }
else 
  {
  for(i=1;i<=m;i++)
    for(j=1;j<=n;j++)
       fscanf(fin,"%d",&a[i][j]);     
  }

memset(el,0,sizeof el);
memset(ec,0,sizeof ec);

int mn=r<c?r:c,k,sol=0;
for(i=1;i<=m;i++)
  for(j=1;j<=n;j++)
     sol+=a[i][j];

for(k=1;k<=mn;k++)
  {
  memset(sl,0,sizeof sl);
  memset(sc,0,sizeof sc);
  for(i=1;i<=m;i++)
    for(j=1;j<=n;j++)
      if(el[i]==0&&ec[j]==0)
       {
       sl[i]+=a[i][j];
       sc[j]+=a[i][j];
       }
      
  nst=0;
  for(i=1;i<=m;i++)
    for(j=1;j<=n;j++)
       if(el[i]==0&&ec[j]==0)
          {
          nst++;                  
          st[nst]=sl[i]+sc[j]-a[i][j];
          lin[nst]=i;
          col[nst]=j;
          }
          
   for(i=1;i<=nst;i++)
     {
     j=i;
     while(j/2&&st[j/2]<st[j])
         {
         intersc(j,j/2);
         j/=2;
         }
     }
     
  i=nst;
  while(i>1)
    {
    intersc(1,i);
    i--;
    
    j=1;
    while(1)
      {
      k=j<<1;
      if(k>i) break;
      if(k+1<=i&&st[k+1]>st[k]) k++;
      if(st[k]<st[j]) break;
      
      intersc(k,j);
      j=k;     
      }              
    }
  
  sol-=st[1];
  el[lin[1]]=1;
  ec[col[1]]=1;       
  }
  
memset(sl,0,sizeof sl);
memset(sc,0,sizeof sc);

for(i=1;i<=m;i++)
  for(j=1;j<=n;j++)
    if(el[i]==0&&ec[j]==0)
        {
        sl[i]+=a[i][j];               
        sc[j]+=a[i][j];
        }
   
for(i=1;i<=m-mn;i++)
   {
   j=i;
   while(j/2&&sl[j/2]<sl[j])
       {
       sl[j/2]^=sl[j];
       sl[j]^=sl[j/2];                     
       sl[j/2]^=sl[j];
       j/=2;
       }                 
   }
i=m-mn;
while(i>1)
 {
 sl[1]^=sl[i];
 sl[i]^=sl[1];                     
 sl[1]^=sl[i];
 i--;
 
 j=1;
 while(1)
  {
  k=2*j;
  if(k>i) break;
  if(k+1<=i&&sl[k+1]>sl[k]) k++;
  if(sl[k]<sl[j]) break;
  
  sl[j]^=sl[k];
  sl[k]^=sl[j];                     
  sl[j]^=sl[k];
  j=k;
  }          
 }   
 
for(i=1;i<=n-mn;i++)
   {
   j=i;
   while(j/2&&sc[j/2]<sc[j])
       {
       sc[j/2]^=sc[j];
       sc[j]^=sc[j/2];                     
       sc[j/2]^=sc[j];
       j/=2;
       }                 
   }
i=n-mn;
while(i>1)
 {
 sc[1]^=sc[i];
 sc[i]^=sc[1];                     
 sc[1]^=sc[i];
 i--;
 
 j=1;
 while(1)
  {
  k=2*j;
  if(k>i) break;
  if(k+1<=i&&sc[k+1]>sc[k]) k++;
  if(sc[k]<sc[j]) break;
  
  sc[j]^=sc[k];
  sc[k]^=sc[j];                     
  sc[j]^=sc[k];
  j=k;
  }          
 }   


        
if(r==mn)
   {
   for(i=1;i<=c-mn;i++)
       sol-=sc[i];
   }
else
  {
  for(i=1;i<=r-mn;i++)
     sol-=sl[i];     
  }
  
fprintf(fout,"%d\n",sol);
fclose(fin);
fclose(fout);
return 0;  
}