解决问题,邻居索引不相同的n个数组列表的一个元素的最小和

时间:2018-09-07 04:28:20

标签: java recursion dynamic-programming

我遇到这样的问题解决问题:

“您决定去购物中心购买衬衫和/或裤子和/或鞋子。在购物中心中,有N个不同的商店。每个商店都包含这三种商品,但价格不同。

现在您有2个习惯:

  • 从每家商店购买确切的商品
  • 如果您已经从当前商店附近的商店购买了该商品,请不要从当前商店购买该商品。 您意识到找钱很困难,因此您想最大程度地减少购物花费。 “

示例 3(N家商店) 1 50 50(商店1中的衬衫,裤子和鞋子的成本) 48 50 50(第2商店的衬衫,裤子和鞋子的成本) 1 50 50(商店3中的衬衫,裤子和鞋子的费用)

因此,我在1号商店购买衬衫,在2号商店购买裤子/鞋,在3号商店购买衬衫的最低成本是52。 我不能在2号店买衬衫,因为我以前在1号店买衬衫。

我的第一个逻辑是使所有可能的清单都在相邻的商店中没有相同的项目,然后我将搜索最低成本... 但是我遇到了时限问题... 有什么想法可以解决吗?

对不起,如果我的英语不好... 非常感谢你们的回答和回答。...

public class Solution {
static ArrayList<ArrayList<Integer>> data;
static int min;
static int sum;
static int n;

static void permutation(int x, int y){
    if(x==n-1){
        sum+=data.get(x).get(y-1);
        if(sum<min)
            min = sum;
    }
    else{
        sum+=data.get(x).get(y-1);
        if(y==1){
            permutation(x+1,2);
            permutation(x+1,3);
        }
        else if(y==2){
            permutation(x+1,1);
            permutation(x+1,3);
        }
        else if(y==3){
            permutation(x+1,1);
            permutation(x+1,2);
        }
    }
    sum-=data.get(x).get(y-1);
}

static int GetMinCost(ArrayList<ArrayList<Integer>> data){
    sum = 0;
    min = Integer.MAX_VALUE;
    permutation(0,1);
    permutation(0,2);
    permutation(0,3);

    return min;
} 

static final Scanner scanner = new Scanner(System.in);

public static void main(String[] args) {       
    int t = scanner.nextInt();
    for(int i=0; i<t; i++){
        n = scanner.nextInt();            
        data = new ArrayList<>();           
        for(int j=0; j<n; j++){
            ArrayList<Integer> cost = new ArrayList<>();
            cost.add(scanner.nextInt());
            cost.add(scanner.nextInt());
            cost.add(scanner.nextInt());
            data.add(cost);
        }           
        System.out.println(GetMinCost(data));           
    }       
}
}

2 个答案:

答案 0 :(得分:0)

假设我正确地理解了这个问题,这就是我将如何在一个预先填充的stores数组中解决它的方法。我们在每个存储阵列中找到最小值,并通过存储和比较索引来排除之前在先前存储中已使用过的索引。

private int stores[][]={{1,50,50},{48,50,50},{1,50,50},{4,3,5},{20,1,20}};


public void solve() {
    int cost=0;
    int lastItemPurchased=-1;
    for (int storeIndex = 0; storeIndex < stores.length; storeIndex++) {
        int lowestPriceInStoreIndex=getMinValueIndex(stores[storeIndex],lastItemPurchased);
        cost+=stores[storeIndex][lowestPriceInStoreIndex];
        lastItemPurchased=lowestPriceInStoreIndex;
    }
    System.out.println("Cost: "+cost);
}
public int getMinValueIndex(int[] numbers,int indexToExclude){
    int minValue = 0;
    for(int i=1;i<numbers.length;i++){
        if(i==indexToExclude)
            continue;
        if(numbers[i] < numbers[minValue]||minValue==indexToExclude){
            minValue = i;
        }
    }
    return minValue;
}

这将输出75,因为它应该为1 + 50 + 1 + 3 + 20。

答案 1 :(得分:0)

我认为一个简单的递归置换功能就足够了-您只需要跟踪最后选择的项目并将其从下一个商店中排除即可。

下面是一些Java代码来说明:

static int minCost(int[][] prices, int store, int cost, int lastItem)
{
    if(store==prices.length) 
        return cost;

    int min = Integer.MAX_VALUE;
    for(int item=0; item<prices[store].length; item++)
    {
        if(item != lastItem)
            min = Math.min(min, minCost(prices, store+1, cost+prices[store][item], item));
    }
    return min;
}

public static void main(String[] args)
{
    int[][] prices1 = {{1,50,50},{48,50,50},{1,50,50}};             
    System.out.println(minCost(prices1, 0, 0, -1));

    int[][] prices2 = {{1,50,50},{48,50,50},{1,50,50},{4,3,5},{20,1,20}};               
    System.out.println(minCost(prices2, 0, 0, -1));
}

输出:

52
58