All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.browseengine.bobo.util.MemoryManager Maven / Gradle / Ivy

Go to download

Bobo is a Faceted Search implementation written purely in Java, an extension of Apache Lucene

The newest version!
/**
 *
 */
package com.browseengine.bobo.util;

import java.lang.ref.WeakReference;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentLinkedQueue;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.concurrent.atomic.AtomicLong;

import org.apache.log4j.Logger;

public class MemoryManager implements MemoryManagerAdminMBean {
  private static final Logger log = Logger.getLogger(MemoryManager.class.getName());
  private static final int[] sizetable;
  private final AtomicLong _hits = new AtomicLong(0);
  private final AtomicLong _miss = new AtomicLong(0);
  static {
    int initsize = 1024;
    double ratio = 1.3;
    int l = (int) (Math.log(Integer.MAX_VALUE / initsize) / Math.log(ratio)) + 1;
    sizetable = new int[l];
    sizetable[0] = initsize;
    for (int i = 1; i < sizetable.length; i++) {
      sizetable[i] = (int) (sizetable[i - 1] * ratio);
    }
  }
  private final ConcurrentHashMap>> _sizeMap = new ConcurrentHashMap>>();
  private volatile ConcurrentLinkedQueue _releaseQueue = new ConcurrentLinkedQueue();
  private volatile ConcurrentLinkedQueue _releaseQueueb = new ConcurrentLinkedQueue();
  private final AtomicInteger _releaseQueueSize = new AtomicInteger(0);
  private final Initializer _initializer;
  private final Thread _cleanThread;

  public MemoryManager(Initializer initializer) {
    this._initializer = initializer;
    _cleanThread = new Thread(new Runnable() {

      @Override
      public void run() {
        T buf = null;
        while (true) {
          synchronized (MemoryManager.this) {
            try {
              MemoryManager.this.wait(10);
            } catch (InterruptedException e) {
              log.error(e);
            }
          }
          ConcurrentLinkedQueue t = _releaseQueue;
          _releaseQueue = _releaseQueueb;
          _releaseQueueb = t;
          while ((buf = _releaseQueueb.poll()) != null) {
            ConcurrentLinkedQueue> queue = _sizeMap.get(_initializer.size(buf));
            // buf is wrapped in WeakReference. this allows GC to reclaim the buffer memory
            _initializer.init(buf);// pre-initializing the buffer in parallel so we save time when
                                   // it is requested later.
            queue.offer(new WeakReference(buf));
            _releaseQueueSize.decrementAndGet();
          }
          buf = null;
        }
      }
    });
    _cleanThread.setDaemon(true);
    _cleanThread.start();
  }

  public MemoryManagerAdminMBean getAdminMBean() {
    return this;
  }

  @Override
  public long getNumCacheMisses() {
    return _miss.get();
  }

  @Override
  public long getNumCacheHits() {
    return _hits.get();
  }

  @Override
  public double getHitRate() {
    long miss = _miss.get();
    long hit = _hits.get();
    return (double) hit / (double) (hit + miss);
  }

  /**
   * @return an initialized instance of type T. The size of the instance may not be the same as the requested size.
   */
  public T get(int reqsize) {
    return _initializer.newInstance(reqsize);
    // long t0 = System.currentTimeMillis();
    // int size = reqsize;
    // for(int i = 0; i= reqsize)
    // {
    // size = sizetable[i];
    // break;
    // }
    // }
    // ConcurrentLinkedQueue> queue = _sizeMap.get(size);
    // if (queue==null)
    // {
    // queue = new ConcurrentLinkedQueue>();
    // _sizeMap.putIfAbsent(size, queue);
    // queue = _sizeMap.get(size);
    // }
    // while(true)
    // {
    // WeakReference ref = (WeakReference) queue.poll();
    // if(ref != null)
    // {
    // T buf = ref.get();
    // if(buf != null)
    // {
    // _hits.incrementAndGet();
    // return buf;
    // }
    // }
    // else
    // {
    // T ret = _initializer.newInstance(size);
    // _miss.incrementAndGet();
    // long hit = _hits.get();
    // if (hit > Long.MAX_VALUE/2)
    // {
    // _hits.set(0);
    // _miss.set(0);
    // }
    // return ret;
    // }
    // }
  }

  /**
   * return the instance to the manager after use
   * @param buf
   */
  public void release(T buf) {
    // if (_releaseQueueSize.get()>8000)
    // {
    // log.info("release queue full");
    // synchronized(MemoryManager.this)
    // {
    // MemoryManager.this.notifyAll();
    // }
    // return;
    // }
    // if(buf != null)
    // {
    // _releaseQueue.offer(buf);
    // _releaseQueueSize.incrementAndGet();
    // synchronized(MemoryManager.this)
    // {
    // MemoryManager.this.notifyAll();
    // }
    // }
  }

  public static interface Initializer {
    public E newInstance(int size);

    public int size(E buf);

    public void init(E buf);
  }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy