/*
  *************************************************************************
 * Copyright (c) 2004 Actuate Corporation.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 *
 * Contributors:
 *  Actuate Corporation  - initial API and implementation
 *  
 *************************************************************************
*/

package org.eclipse.birt.data.engine.aggregation;

import org.eclipse.birt.data.engine.aggregation.rank.TotalIsBottomN;
import org.eclipse.birt.data.engine.aggregation.rank.TotalIsBottomNPercent;
import org.eclipse.birt.data.engine.aggregation.rank.TotalPercentRank;
import org.eclipse.birt.data.engine.aggregation.rank.TotalPercentSum;
import org.eclipse.birt.data.engine.aggregation.rank.TotalPercentile;
import org.eclipse.birt.data.engine.aggregation.rank.TotalQuartile;
import org.eclipse.birt.data.engine.aggregation.rank.TotalRank;
import org.eclipse.birt.data.engine.aggregation.rank.TotalIsTopN;
import org.eclipse.birt.data.engine.aggregation.rank.TotalIsTopNPercent;
import org.eclipse.birt.data.engine.api.aggregation.IAggregation;

/**
 * This class provides instances of all built-in BIRT aggregations.
 */
public class BuiltInAggregationFactory 
{
    public static final String	TOTAL_COUNT_FUNC 		= "COUNT";
    public static final String	TOTAL_SUM_FUNC 			= "SUM";

    public static final String 	TOTAL_MAX_FUNC			= "MAX";
    public static final String	TOTAL_MIN_FUNC			= "MIN";
    public static final String	TOTAL_AVE_FUNC			= "AVE";
    public static final String 	TOTAL_WEIGHTEDAVE_FUNC	= "WEIGHTEDAVE";
    public static final String 	TOTAL_MOVINGAVE_FUNC	= "MOVINGAVE";
    public static final String 	TOTAL_MEDIAN_FUNC		= "MEDIAN";
    public static final String	TOTAL_MODE_FUNC			= "MODE";
    public static final String	TOTAL_STDDEV_FUNC		= "STDDEV";
    public static final String	TOTAL_VARIANCE_FUNC		= "VARIANCE";
    public static final String	TOTAL_FIRST_FUNC		= "FIRST";
    public static final String	TOTAL_LAST_FUNC			= "LAST";
    public static final String	TOTAL_RUNNINGSUM_FUNC	= "RUNNINGSUM";
    
    public static final String 	TOTAL_IRR_FUNC			="IRR";
    public static final String 	TOTAL_MIRR_FUNC			="MIRR";
    public static final String 	TOTAL_NPV_FUNC			="NPV";
    public static final String 	TOTAL_RUNNINGNPV_FUNC	="RUNNINGNPV";
    public static final String 	TOTAL_COUNTDISTINCT_FUNC	="COUNTDISTINCT";
    
    public static final String  TOTAL_RANK_FUNC         = "RANK";
    public static final String  TOTAL_TOP_N_FUNC		= "ISTOPN";
    public static final String  TOTAL_TOP_PERCENT_FUNC  = "ISTOPNPERCENT";
    public static final String  TOTAL_BOTTOM_N_FUNC		= "ISBOTTOMN";
    public static final String 	TOTAL_BOTTOM_PERCENT_FUNC  = "ISBOTTOMNPERCENT";
    public static final String  TOTAL_PERCENT_RANK_FUNC = "PERCENTRANK";
    public static final String  TOTAL_PERCENTILE_FUNC   = "PERCENTILE";
    public static final String  TOTAL_QUARTILE_FUNC		= "QUARTILE";
    public static final String  TOTAL_PERCENTSUM_FUNC 	= "PERCENTSUM";
    
    public static final String  TOTAL_RUNNINGCOUNT_FUNC		= "RUNNINGCOUNT";
    // ... TODO: more
    //public static final String	TOTAL_DISTCOUNT_FUNC	= "DISTINCT_COUNT";
    private static BuiltInAggregationFactory instance = null;
    private static IAggregation[] aggregations =
    {
            // Make sure that this array matches the order of the TOTAL_xx constants
            new TotalCount(),
            new TotalSum(), 
            new TotalMax(),
            new TotalMin(),
            new TotalAve(),
            new TotalMovingAve(),
            new TotalWeightedAve(),
            new TotalMedian(),
            new TotalMode(),
            new TotalStdDev(),
            new TotalVariance(),
            new TotalFirst(),
            new TotalLast(),
            new TotalRunningSum(),
            new TotalIrr(),
            new TotalMirr(),
            new TotalNpv(),
            new TotalRunningNpv(),
			new TotalCountDistinct(),
			new TotalRank(),
			new TotalIsTopN(),
			new TotalIsTopNPercent(),
			new TotalIsBottomN(),
			new TotalIsBottomNPercent(),
			new TotalPercentRank(),
			new TotalPercentile(),
			new TotalQuartile(),
			new TotalPercentSum(),
			new TotalRunningCount()
			
//			TODO: ...
    };
    private static String[] aggNames = {
    	TOTAL_COUNT_FUNC,
        TOTAL_SUM_FUNC,
        TOTAL_MAX_FUNC,
        TOTAL_MIN_FUNC,
        TOTAL_AVE_FUNC,
        TOTAL_WEIGHTEDAVE_FUNC,
        TOTAL_MOVINGAVE_FUNC,
        TOTAL_MEDIAN_FUNC,
        TOTAL_MODE_FUNC,
        TOTAL_STDDEV_FUNC,
        TOTAL_VARIANCE_FUNC,
        TOTAL_FIRST_FUNC,
        TOTAL_LAST_FUNC,
        TOTAL_RUNNINGSUM_FUNC,
        
        TOTAL_IRR_FUNC,
        TOTAL_MIRR_FUNC,
        TOTAL_NPV_FUNC,
        TOTAL_RUNNINGNPV_FUNC,
        TOTAL_COUNTDISTINCT_FUNC,
        
        TOTAL_RANK_FUNC,
        TOTAL_TOP_N_FUNC,
        TOTAL_TOP_PERCENT_FUNC,
        TOTAL_BOTTOM_N_FUNC,
        TOTAL_BOTTOM_PERCENT_FUNC,
        
        TOTAL_PERCENT_RANK_FUNC,
        TOTAL_PERCENTILE_FUNC,
        TOTAL_QUARTILE_FUNC,
        TOTAL_PERCENTSUM_FUNC,
        
        TOTAL_RUNNINGCOUNT_FUNC
    }; 
    
    private BuiltInAggregationFactory()
    {};
    
    /**
     * @return
     */
    public static BuiltInAggregationFactory getInstance( )
	{
		if ( instance == null )
		{
			synchronized ( BuiltInAggregationFactory.class )
			{
				if ( instance == null )
					instance = new BuiltInAggregationFactory( );
			}
		}

		return instance;
	}
    

                               
    /**
     * Gets an instance of the built-in Aggregation identified by name.
     * @param name Name (e.g., "SUM", "AVG", etc.) of the built-in aggregation. This name is
     * case insensitive
     * @return Instance of the requested Aggregation, or null if no such name is found. 
     */
    public IAggregation getAggregation( String name )
    {
        // TODO:  create a hash map from String to Function index so this look up
        // is fast
        for ( int i = 0; i < aggregations.length; i ++ )
        {
            if ( aggregations[i].getName().compareToIgnoreCase( name ) == 0 )
                return aggregations[i];
        }
        return null;
    }

	public String[] getAggregationNames( )
	{
		return aggNames;
	}
}


