// Path: src/com/juliasoft/beedeedee/factories/Factory.java
// public static interface GarbageCollectionListener {
// 
// 	/**
// 	 * Called when a garbage collection operation is about to start.
// 	 * 
// 	 * @param num the progressive number of the garbage collection operation
// 	 * @param size the number of nodes in the garbage collected table
// 	 * @param free the number of free nodes after the operation
// 	 * @param totalTime the cumulative garbage collection time up to now
// 	 */
// 
// 	public void onStart(int num, int size, int free, long totalTime);
// 
// 	/**
// 	 * Called when a garbage collection operation has been performed.
// 	 * 
// 	 * @param num the progressive number of the garbage collection operation
// 	 * @param size the number of nodes in the garbage collected table
// 	 * @param free the number of free nodes after the operation
// 	 * @param time the time required for the garbage collection
// 	 * @param totalTime the cumulative garbage collection time up to now
// 	 */
// 
// 	public void onStop(int num, int size, int free, long time, long totalTime);
// }
// 
// Path: src/com/juliasoft/beedeedee/factories/Factory.java
// public static interface ResizeListener {
// 
// 	/**
// 	 * Called when a resize operation is about to start.
// 	 * 
// 	 * @param num the progressive number of the resize operation
// 	 * @param oldSize the old size of the table
// 	 * @param newSize the new size of the table
// 	 * @param totalTime the cumulative resize time up to now
// 	 */
// 
// 	public void onStart(int num, int oldSize, int newSize, long totalTime);
// 
// 	/**
// 	 * Called when a resize operation has been performed.
// 	 * 
// 	 * @param num the progressive number of the resize operation
// 	 * @param oldSize the old size of the table
// 	 * @param newSize the new size of the table
// 	 * @param time the time required for the resize
// 	 * @param totalTime the cumulative resize time up to now
// 	 */
// 
// 	public void onStop(int num, int oldSize, int newSize, long time, long totalTime);
// }


import java.util.concurrent.ExecutionException;
import java.util.concurrent.ForkJoinPool;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.concurrent.locks.ReentrantLock;
import java.util.stream.IntStream;
import com.juliasoft.beedeedee.factories.Factory.GarbageCollectionListener;
import com.juliasoft.beedeedee.factories.Factory.ResizeListener;
/* 
  Copyright 2014 Julia s.r.l.
    
  This file is part of BeeDeeDee.

  BeeDeeDee is free software: you can redistribute it and/or modify
  it under the terms of the GNU General Public License as published by
  the Free Software Foundation, either version 3 of the License, or
  (at your option) any later version.

  BeeDeeDee is distributed in the hope that it will be useful,
  but WITHOUT ANY WARRANTY; without even the implied warranty of
  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  GNU General Public License for more details.

  You should have received a copy of the GNU General Public License
  along with BeeDeeDee.  If not, see <http://www.gnu.org/licenses/>.
*/
package com.juliasoft.beedeedee.factories;



public class ResizingAndGarbageCollectedUniqueTable extends SimpleUniqueTable {

	private final ForkJoinPool pool = new ForkJoinPool(Runtime.getRuntime().availableProcessors());

	/**
	 * The maximal number of nodes that is added at each resize operation.
	 */

	private volatile int maxIncrease = 1000000;

	/**
	 * The factor by which the table of nodes gets increased at each resize.
	 */

	private volatile double increaseFactor = 2;

	/**
	 * The cache ratio for the operator caches. When the node table grows,
	 * operator caches will also grow to maintain the ratio.
	 */

	private volatile double cacheRatio = 0.5;

	/**
	 * The minimum percentage of nodes to be reclaimed after a garbage collection.
	 * If this percentage is not reclaimed, the node table will be grown.
	 * The range for this value is 0..1.
	 */

	private volatile double minFreeNodes = 0.2;

	private final Factory factory;

	private long totalResizeTime;

	private final AtomicInteger hashCodeAuxCounter = new AtomicInteger();

	/**
	 * The number of resize operations performed so far.
	 */

	private int numOfResizes;

	private long totalGCTime;

	/**
	 * The number of garbage collections performed so far.
	 */

	private int numOfGCs;

	/**
	 * The garbage collection listener, if any.
	 */

	private GarbageCollectionListener gcListener;

	/**
	 * The resize collection listener, if any.
	 */

// Path: src/com/juliasoft/beedeedee/factories/Factory.java
// public static interface GarbageCollectionListener {
// 
// 	/**
// 	 * Called when a garbage collection operation is about to start.
// 	 * 
// 	 * @param num the progressive number of the garbage collection operation
// 	 * @param size the number of nodes in the garbage collected table
// 	 * @param free the number of free nodes after the operation
// 	 * @param totalTime the cumulative garbage collection time up to now
// 	 */
// 
// 	public void onStart(int num, int size, int free, long totalTime);
// 
// 	/**
// 	 * Called when a garbage collection operation has been performed.
// 	 * 
// 	 * @param num the progressive number of the garbage collection operation
// 	 * @param size the number of nodes in the garbage collected table
// 	 * @param free the number of free nodes after the operation
// 	 * @param time the time required for the garbage collection
// 	 * @param totalTime the cumulative garbage collection time up to now
// 	 */
// 
// 	public void onStop(int num, int size, int free, long time, long totalTime);
// }
// 
// Path: src/com/juliasoft/beedeedee/factories/Factory.java
// public static interface ResizeListener {
// 
// 	/**
// 	 * Called when a resize operation is about to start.
// 	 * 
// 	 * @param num the progressive number of the resize operation
// 	 * @param oldSize the old size of the table
// 	 * @param newSize the new size of the table
// 	 * @param totalTime the cumulative resize time up to now
// 	 */
// 
// 	public void onStart(int num, int oldSize, int newSize, long totalTime);
// 
// 	/**
// 	 * Called when a resize operation has been performed.
// 	 * 
// 	 * @param num the progressive number of the resize operation
// 	 * @param oldSize the old size of the table
// 	 * @param newSize the new size of the table
// 	 * @param time the time required for the resize
// 	 * @param totalTime the cumulative resize time up to now
// 	 */
// 
// 	public void onStop(int num, int oldSize, int newSize, long time, long totalTime);
// }


// Path: src/com/juliasoft/beedeedee/factories/ResizingAndGarbageCollectedUniqueTable.java
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ForkJoinPool;
import java.util.concurrent.atomic.AtomicInteger;
import java.util.concurrent.locks.ReentrantLock;
import java.util.stream.IntStream;
import com.juliasoft.beedeedee.factories.Factory.GarbageCollectionListener;
import com.juliasoft.beedeedee.factories.Factory.ResizeListener;

/* 
  Copyright 2014 Julia s.r.l.
    
  This file is part of BeeDeeDee.

  BeeDeeDee is free software: you can redistribute it and/or modify
  it under the terms of the GNU General Public License as published by
  the Free Software Foundation, either version 3 of the License, or
  (at your option) any later version.

  BeeDeeDee is distributed in the hope that it will be useful,
  but WITHOUT ANY WARRANTY; without even the implied warranty of
  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  GNU General Public License for more details.

  You should have received a copy of the GNU General Public License
  along with BeeDeeDee.  If not, see <http://www.gnu.org/licenses/>.
*/
package com.juliasoft.beedeedee.factories;



public class ResizingAndGarbageCollectedUniqueTable extends SimpleUniqueTable {

	private final ForkJoinPool pool = new ForkJoinPool(Runtime.getRuntime().availableProcessors());

	/**
	 * The maximal number of nodes that is added at each resize operation.
	 */

	private volatile int maxIncrease = 1000000;

	/**
	 * The factor by which the table of nodes gets increased at each resize.
	 */

	private volatile double increaseFactor = 2;

	/**
	 * The cache ratio for the operator caches. When the node table grows,
	 * operator caches will also grow to maintain the ratio.
	 */

	private volatile double cacheRatio = 0.5;

	/**
	 * The minimum percentage of nodes to be reclaimed after a garbage collection.
	 * If this percentage is not reclaimed, the node table will be grown.
	 * The range for this value is 0..1.
	 */

	private volatile double minFreeNodes = 0.2;

	private final Factory factory;

	private long totalResizeTime;

	private final AtomicInteger hashCodeAuxCounter = new AtomicInteger();

	/**
	 * The number of resize operations performed so far.
	 */

	private int numOfResizes;

	private long totalGCTime;

	/**
	 * The number of garbage collections performed so far.
	 */

	private int numOfGCs;

	/**
	 * The garbage collection listener, if any.
	 */

	private GarbageCollectionListener gcListener;

	/**
	 * The resize collection listener, if any.
	 */

	private ResizeListener resizeListener;