将一个键值映射到Map中另一个键值的算法

时间:2011-07-22 13:14:26

标签: java algorithm map

我有一些地图,我想计算笛卡尔积。有人可以建议一个好的算法:

数据:

Key1    {100,101,102}

Key2    {200,201}

Key3    {300}

必填项:(订单确实很重要)

100,200,300
101,200,300
102,200,300
100,201,300
101,201,300
102,201,300

地图是动态的,因此键和值的大小可能会有所不同。

感谢。

3 个答案:

答案 0 :(得分:1)

您需要切换到使用LinkedHashMap,以便在迭代键时保留顺序。

import java.util.ArrayList;
import java.util.Arrays;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;

public class CartesianPrint {

    public static void main(String[] args) {
        Map<Integer,List<Integer>> groupMap = new LinkedHashMap<Integer,List<Integer>>();

        groupMap.put(1,Arrays.asList(new Integer[]{100,101,102}));
        groupMap.put(2,Arrays.asList(new Integer[]{200,201}));
        groupMap.put(3,Arrays.asList(new Integer[]{300}));

        List<List<Integer>> values = new ArrayList<List<Integer>>(groupMap.values());
        int[] printList = new int[values.size()];
        print(values,printList,values.size()-1);        
    }

    static void print(List<List<Integer>> values, int[] printList, int level){
        for (Integer value: values.get(level)) {
            printList[level] = value;
            if(level == 0){
                 System.out.println(Arrays.toString(printList));
            }else{
                 print(values,printList,level-1);
            }
        }       
    }

}

答案 1 :(得分:1)

与OndraŽižka相同,如果您不需要地图,请使用List,它的工作方式相同。 这是一种不那么优化的方式(我应该克隆而不是在递归中重新计算产品。但是这个想法仍然在这里而且很短。我特别注意保持正确的顺序,这就是我向后运行List的原因。

    public static List<List<Integer>> getCart(List<List<Integer>> a_list) {
        List<List<Integer>> l_result = new ArrayList<List<Integer>>();
        if (a_list == null || a_list.isEmpty()) {
            l_result.add(new ArrayList<Integer>());
            return l_result;
        }
        for (Integer l_value : a_list.get(a_list.size()-1)) {
            List<List<Integer>> l_resultPortion = getCart(a_list.subList(0, a_list.size() - 1));
            for (List<Integer> l_list : l_resultPortion) {
                l_list.add(l_value);
            }
            l_result.addAll(l_resultPortion);
        }
        return l_result;
    }

答案 2 :(得分:0)

我建议创建一个元组存储(在你的例子中为三元组)。

List<List<Integer>> store = new LinkedList();

然后创建一个Stack个数字。

Stack<Integer> stack = new Stack();

然后写一个递归函数:

在每个递归函数调用中,将实际处理的数组值推入堆栈,并将当前元组添加到商店。

private static process( Iterator<String> keys ){
    // Bottom-most key
    if( ! keys.hasNext() ){
        // Construct the tuple from the stack and add it to store.
    }
    else {
       String currentKey = keys.next();
       List<Integer> numbers = map.get( currentKey );
       for( int i : numbers ){
          stack.push( i );
          process ( keys );
          stack.pop();  // Dispose processed number.
       }
    }
}

我希望我能正确解决问题(不保证)。 很抱歉没有完整,但这是你的功课:)