Cod sursa(job #223696)

Utilizator mika17Mihai Alex Ionescu mika17 Data 29 noiembrie 2008 01:43:32
Problema Oite Scor 10
Compilator cpp Status done
Runda Arhiva de probleme Marime 3.71 kb
#include <fstream>
#include <cstring>

#define NMAX 1024

using namespace std;

class hash {

        public:

        typedef short it_type;

        struct d_type
        {
         int sum;
         short fi,se;
         bool operator==(d_type X)
         {
          return X.sum == sum && X.fi == fi && X.se == se;
         }
        };

        struct entry
        {
         d_type data;
         it_type next;
        } * table;

        int size;

        bool is_multimap;

        it_type pos;

        static d_type EMPTY,DELETED;

        hash()
        {
         size = NMAX*NMAX*2;

         table = new entry[size];

         memset(table,0,sizeof table);

         is_multimap = true;
        }

        d_type convert(int s,int i,int j)
        {
         d_type tmp = {s,i,j};
         return tmp;
        }

        inline int h1(int K)
        {
         return K & (size-1);
        }

        inline int h2(int K)
        {
         return 1 + (K & (size-1) ) | 1;
        }

        inline int h(int K,int i)
        {
         return ( h1(K) + i * h2(K) ) & (size-1);
        }

        void insert(d_type X)
        {
         it_type j = -1;

         for(int i = 0; i < size ; ++i)
         {
          int p = h(X . sum, i);

          if(table[p] . data == EMPTY || table[p] . data == DELETED)
          {
           table[p] . data = X;  table[p] . next = -1;

           if(j != -1) table[j] . next = p;

           break;
          }
           else
            if(table[p] . data . sum == X . sum)
             if(!is_multimap) return;
              else j = p;
         }
        }

        it_type find_first(int K)
        {
         pos = -1;

         for(int i = 0 ; i < size ; ++i)
         {
          int p = h(K, i);

          if(table[p] . data == EMPTY) break;

          if(table[p] . data . sum == K)
          {
           pos = p;
           break;
          }
         }

         return pos;
        }

        void erase(d_type X)
        {
         it_type j = -1;
         
         for(int i = 0; i < size; ++i)
         {
          int p = h(X . sum, i);
          if(table[p] . data == X)
          {
           j = p;
           break;
          }
         }

         if(j == -1) return; //nu a gasit cheia X in hash

         do
         {
          table[j] . data = DELETED;
          j = table[j] . next;
         }
         while (j != -1);
          
        }

        it_type find_next(int K)
        {
          if(pos != -1 && table[pos] . data . sum == K)
            return (pos = table[pos] . next);
          return -1;
        }
        /*
        void debug()
        {
         for(int i = 0 ; i < 100; ++i)
         {
          fout <<i <<' ' << table[i] . data . sum << ' ' << table[i].data.fi << ' ' <<table[i].data.se <<' '<<table[i].next<<'\n';
         }
        }*/
};

hash::d_type hash::EMPTY = {0,0,0},hash::DELETED = {-2,-2,-2};


int main()
{
        hash H = hash();
        
        ifstream fin("oite.in");
        ofstream fout("oite.out");

        int N,L,A[NMAX];

        fin>>N>>L;

        for(int i = 0; i < N; ++i)
         fin>>A[i];

        for(int i = 0; i < N - 1; ++i)
         for(int j = i + 1; j < N; ++j)
           H . insert(H.convert(A[i] + A[j],i,j));

        int cnt = 0;
        for(int i = 0 ; i < N - 1; ++i)
         for(int j = i + 1; j < N ; ++j)

          for(int t = H.find_first(L - A[i] - A[j]) ;t != -1; t = H.find_next(L - A[i] - A[j]) )
          {
            if(t != -1 && H.table[t] . data . fi > j)
             ++cnt;
          }


        fout<<cnt;

        return 0;
}