如何用传递依存关系/图形解决算法问题?

时间:2019-04-14 16:59:03

标签: algorithm data-structures graph dfs transitive-dependency

在面试中被问到这些问题时,我有点挣扎。举例来说,我有一个问题,我需要在哪里找到从一种货币转换为另一种货币的货币金额,并得到货币清单。如何建立邻接关系/关系映射,以便可以获取正确的数量。即使是解释逻辑的算法也足够了。感谢您对此的建议!

例如:

比方说,我给了我一个包含不同转换率的货币对象列表(USD-> INR = 75,INR-> XXX = 100)。我需要找到USD-> XXX = 7500的转换。我也应该可以反向进行转换,例如INR-> USD。如何通过建立图来找到它?。

public Currency{
String fromCurrency;
String toCurrency;
double rate;
}

public double currencyConverter(List<Currency> currencies, fromCurrency, toCurrency){

return convertedCurrency;
}

2 个答案:

答案 0 :(得分:0)

在您提到的问题中,图形是有向图。假设您使用邻接矩阵表示图。用所有货币的数据填充矩阵。例如,USD-> INR的汇率为R1,因此INR-> USD的汇率为1 / R1。填充邻接矩阵后,请使用algorithms to compute transitive closure of a directed graph,例如Floyd–Warshall algorithm

答案 1 :(得分:0)

我不确定如何使用Floyd-Warshall算法来解决此问题。但是,我能够使用动态编程解决此问题。这是我的解决方案:

class Currency{

    String fromCurrency;
    String toCurrency;
    double rate;

    public Currency(String fromCurrency, String toCurrency, double rate) {
        this.fromCurrency = fromCurrency;
        this.toCurrency = toCurrency;
        this.rate = rate;
    }
}

public class CurrencyConverter {

    public static double currencyConverter(List<Currency> currencies, String fromCurrency, String toCurrency) {

        Set<String> currencyNotes = new LinkedHashSet<>();

        for(Currency currency : currencies) {
            currencyNotes.add(currency.fromCurrency);
            currencyNotes.add(currency.toCurrency);
        }

        Map<String, Integer> currencyMap = new TreeMap<>();
        int idx = 0;

        for(String currencyNote : currencyNotes) {
            currencyMap.putIfAbsent(currencyNote, idx++);
        }

        double[][] dp = new double[currencyNotes.size()][currencyNotes.size()];

        for(double[] d : dp) {
            Arrays.fill(d, -1.0);
        }

        for(int i=0;i<currencyNotes.size();i++) {
            dp[i][i] = 1;
        }

        for(Currency currency : currencies) {
            Integer fromCurrencyValue = currencyMap.get(currency.fromCurrency);
            Integer toCurrencyValue = currencyMap.get(currency.toCurrency);

            dp[fromCurrencyValue][toCurrencyValue] = currency.rate;
            dp[toCurrencyValue][fromCurrencyValue] = 1/(currency.rate);
        }

        for(int i=currencyNotes.size()-2;i>=0;i--) {
            for(int j= i+1;j<currencyNotes.size();j++) {
                dp[i][j] = dp[i][j-1]*dp[i+1][j]/(dp[i+1][j-1]);
                dp[j][i] = 1/dp[i][j];
            }
        }

        return dp[currencyMap.get(fromCurrency)][currencyMap.get(toCurrency)];

    }

我认为解决传递依赖问题的最佳方法是首先确定节点及其关系,然后对其进行回溯。正如来自黑暗骑士的小丑所说的:“有时只需要一点推动力即可:”