Cod sursa(job #2824372)

Utilizator mircea_007Mircea Rebengiuc mircea_007 Data 1 ianuarie 2022 22:49:40
Problema Heapuri Scor 20
Compilator cpp-64 Status done
Runda Arhiva educationala Marime 2.62 kb
#include <stdio.h>
#include <ctype.h>

#define MAXN 200000

FILE *fin, *fout;

class MinHeap {
  protected:
    int n, ntrack;
    int heap[MAXN];    // indici in values[]
    int values[MAXN];  // valorile numerelor
    int tracker[MAXN]; // indici in heap[]
    
    inline int cmp( int i, int j ){
      return values[heap[i]] - values[heap[j]];
    }
    
    inline void swap( int i, int j ){
      int aux;
      
      aux = tracker[heap[i]];
      tracker[heap[i]] = tracker[heap[j]];
      tracker[heap[j]] = aux;
      
      aux = heap[i];
      heap[i] = heap[j];
      heap[j] = aux;
    }
    
    inline int minLRP( int i ){
      int c = 2 * i + 1, min = i;
      
      if( c < n && cmp( c, min ) < 0 )
        min = c;
      
      c++;
      
      if( c < n && cmp( c, min ) < 0 )
        min = c;
      
      return min;
    }
    
    inline void fall( int i ){
      int next;
      
      while( (next = minLRP( i )) != i ){
        swap( i, next );
        i = next;
      }
    }
  
    inline void rise( int i ){
      int next;
      
      while( cmp( i, next = ((i - 1) / 2) ) < 0 ){
        swap( i, next );
        i = next;
      }
    }

  public:
    MinHeap(){
      n = ntrack = 0;
    }
    
    inline void insert( int x ){
      values[ntrack] = x;
      tracker[ntrack] = n;
      heap[n++] = ntrack++;
      
      rise( n - 1 );
    }
    
    inline void del( int i ){
      int pos = tracker[i];
      
      if( pos == -1 )
        return;// i dunno what to do
      
      tracker[i] = -1;
      n--;
      swap( pos, n );
      if( cmp( pos, (pos - 1) / 2 ) < 0 )
        rise( pos );
      else
        fall( pos );
    }
    
    inline int min(){
      return values[heap[0]];
    }
    
    void printHeap( int root, int indent ){
      int i;
      
      if( root < n ){
        printHeap(root * 2 + 1, indent + 1);
        
        for( i = indent ; i-- ; )
          fputs("  ", stderr);
        fprintf(stderr, "%d\n", values[heap[root]]);
        
        printHeap(root * 2 + 2, indent + 1);
      }
    }
};

static inline int fgetint(){
  int n = 0, ch;
  
  while( !isdigit( ch = fgetc( fin ) ) );
  do
    n = n * 10 + ch - '0';
  while( isdigit( ch = fgetc( fin ) ) );
  
  return n;
}

int main(){
  fin  = fopen( "heapuri.in",  "r" );
  fout = fopen( "heapuri.out", "w" );
  
  MinHeap heap;

  int q;
  
  for( q = fgetint() ; q-- ; ){
    switch( fgetint() ){
      case 1:
        heap.insert( fgetint() );
        break;
      case 2:
        heap.del( fgetint() - 1 );
        break;
      case 3:
        fprintf(fout, "%d\n", heap.min());
        break;
    }
  }
  
  fclose(fin);
  fclose(fout);
  return 0;
}