// Path: src/main/java/au/net/woodberry/ta/toolbox/enums/Group.java
// public enum Group {
//     SHORTTERM, LONGTERM
// }
// 
// Path: src/main/java/au/net/woodberry/ta/toolbox/enums/Period.java
// public enum Period {
// 
//     // Short term moving averages
//     THREE(3, Group.SHORTTERM),
//     FIVE(5, Group.SHORTTERM),
//     SEVEN(7, Group.SHORTTERM),
//     EIGHT(8, Group.SHORTTERM),
//     NINE(9, Group.SHORTTERM),
//     TEN(10, Group.SHORTTERM),
//     ELEVEN(11, Group.SHORTTERM),
//     TWELVE(12, Group.SHORTTERM),
//     THIRTEEN(13, Group.SHORTTERM),
//     FIFTEEN(15, Group.SHORTTERM),
// 
//     // Long term moving averages
//     TWENTYONE(21, Group.LONGTERM),
//     TWENTYFOUR(24, Group.LONGTERM),
//     TWENTYSEVEN(27, Group.LONGTERM),
//     THIRTY(30, Group.LONGTERM),
//     THIRTYTHREE(33, Group.LONGTERM),
//     THIRTYFIVE(35, Group.LONGTERM),
//     THIRTYSIX(36, Group.LONGTERM),
//     FORTY(40, Group.LONGTERM),
//     FORTYFIVE(45, Group.LONGTERM),
//     FIFTY(50, Group.LONGTERM),
//     SIXTY(60, Group.LONGTERM);
// 
//     private final int timeFrame;
//     private final Group group;
// 
//     Period(int timeFrame, Group group) {
//         this.timeFrame = timeFrame;
//         this.group = group;
//     }
// 
//     public Group getGroup() {
//         return group;
//     }
// 
//     public int getTimeFrame() {
//         return timeFrame;
//     }
// }


import au.net.woodberry.ta.toolbox.enums.Group;
import au.net.woodberry.ta.toolbox.enums.Period;
import com.google.common.base.Predicate;
import com.google.common.collect.Maps;
import eu.verdelhan.ta4j.TADecimal;
import java.util.ArrayList;
import java.util.Comparator;
import java.util.List;
import java.util.Map;
import java.util.TreeMap;
package au.net.woodberry.ta.toolbox.object;



public class MultipleMovingAverage {

    // Total number of moving averages
    private static final int MAP_SIZE = 12;
    
    // Map sorted by the period's time frame
    private Map<Period, TADecimal> objectMap = new TreeMap<>(new Comparator<Period>() {
        @Override
        public int compare(Period p1, Period p2) {
            return p1.getTimeFrame() == p2.getTimeFrame() ? 0 : p1.getTimeFrame() > p2.getTimeFrame() ? 1 : -1;
        }
    });
    
    public void setValue(Period period, TADecimal value) {
        objectMap.put(period, value);
    }

    /**
     * Determines the shortest period for this multiple moving average.
     * @param group The group to determine the shortest period for.
     * @return The shortest period. May be null if the group could not be determined
     */
    public Period shortestOf(Group group) {
        // Create a list from the map, filtered by group and return the first entry (shortest period)
        ArrayList<Period> periods = new ArrayList<>(Maps.filterEntries(objectMap, groupPredicate(group)).keySet());
        return periods.get(0);
    }

    /**
     * Determines the longest period for this multiple moving average.
     * @param group The group to determine the longest period for.
     * @return The longest period. May be null if the group could not be determined
     */
// Path: src/main/java/au/net/woodberry/ta/toolbox/enums/Group.java
// public enum Group {
//     SHORTTERM, LONGTERM
// }
// 
// Path: src/main/java/au/net/woodberry/ta/toolbox/enums/Period.java
// public enum Period {
// 
//     // Short term moving averages
//     THREE(3, Group.SHORTTERM),
//     FIVE(5, Group.SHORTTERM),
//     SEVEN(7, Group.SHORTTERM),
//     EIGHT(8, Group.SHORTTERM),
//     NINE(9, Group.SHORTTERM),
//     TEN(10, Group.SHORTTERM),
//     ELEVEN(11, Group.SHORTTERM),
//     TWELVE(12, Group.SHORTTERM),
//     THIRTEEN(13, Group.SHORTTERM),
//     FIFTEEN(15, Group.SHORTTERM),
// 
//     // Long term moving averages
//     TWENTYONE(21, Group.LONGTERM),
//     TWENTYFOUR(24, Group.LONGTERM),
//     TWENTYSEVEN(27, Group.LONGTERM),
//     THIRTY(30, Group.LONGTERM),
//     THIRTYTHREE(33, Group.LONGTERM),
//     THIRTYFIVE(35, Group.LONGTERM),
//     THIRTYSIX(36, Group.LONGTERM),
//     FORTY(40, Group.LONGTERM),
//     FORTYFIVE(45, Group.LONGTERM),
//     FIFTY(50, Group.LONGTERM),
//     SIXTY(60, Group.LONGTERM);
// 
//     private final int timeFrame;
//     private final Group group;
// 
//     Period(int timeFrame, Group group) {
//         this.timeFrame = timeFrame;
//         this.group = group;
//     }
// 
//     public Group getGroup() {
//         return group;
//     }
// 
//     public int getTimeFrame() {
//         return timeFrame;
//     }
// }


// Path: src/main/java/au/net/woodberry/ta/toolbox/object/MultipleMovingAverage.java
import au.net.woodberry.ta.toolbox.enums.Group;
import au.net.woodberry.ta.toolbox.enums.Period;
import com.google.common.base.Predicate;
import com.google.common.collect.Maps;
import eu.verdelhan.ta4j.TADecimal;
import java.util.ArrayList;
import java.util.Comparator;
import java.util.List;
import java.util.Map;
import java.util.TreeMap;

package au.net.woodberry.ta.toolbox.object;



public class MultipleMovingAverage {

    // Total number of moving averages
    private static final int MAP_SIZE = 12;
    
    // Map sorted by the period's time frame
    private Map<Period, TADecimal> objectMap = new TreeMap<>(new Comparator<Period>() {
        @Override
        public int compare(Period p1, Period p2) {
            return p1.getTimeFrame() == p2.getTimeFrame() ? 0 : p1.getTimeFrame() > p2.getTimeFrame() ? 1 : -1;
        }
    });
    
    public void setValue(Period period, TADecimal value) {
        objectMap.put(period, value);
    }

    /**
     * Determines the shortest period for this multiple moving average.
     * @param group The group to determine the shortest period for.
     * @return The shortest period. May be null if the group could not be determined
     */
    public Period shortestOf(Group group) {
        // Create a list from the map, filtered by group and return the first entry (shortest period)
        ArrayList<Period> periods = new ArrayList<>(Maps.filterEntries(objectMap, groupPredicate(group)).keySet());
        return periods.get(0);
    }

    /**
     * Determines the longest period for this multiple moving average.
     * @param group The group to determine the longest period for.
     * @return The longest period. May be null if the group could not be determined
     */
    public Period longestOf(Group group) {