399. Evaluate Division

  • Difficulty: Medium

  • Topics: Union Find, Graph

  • Similar Questions:

Problem:

Equations are given in the format A / B = k, where A and B are variables represented as strings, and k is a real number (floating point number). Given some queries, return the answers. If the answer does not exist, return -1.0.

Example:
Given a / b = 2.0, b / c = 3.0.
queries are: a / c = ?, b / a = ?, a / e = ?, a / a = ?, x / x = ? .
return [6.0, 0.5, -1.0, 1.0, -1.0 ].

The input is: vector<pair<string, string>> equations, vector<double>& values, vector<pair<string, string>> queries , where equations.size() == values.size(), and the values are positive. This represents the equations. Return vector<double>.

According to the example above:

equations = [ ["a", "b"], ["b", "c"] ],
values = [2.0, 3.0],
queries = [ ["a", "c"], ["b", "a"], ["a", "e"], ["a", "a"], ["x", "x"] ]. 

 

The input is always valid. You may assume that evaluating the queries will result in no division by zero and there is no contradiction.

Solutions:

class Solution {
public:
    vector<double> calcEquation(vector<vector<string>>& equations, vector<double>& values, vector<vector<string>>& queries) {
        UF uf;
        for (int i = 0; i < equations.size(); ++i) {
            uf.connect(equations[i][0], equations[i][1], values[i]);
        }

        vector<double> ret;
        for (auto q : queries) {
            ret.push_back(uf.query(q[0], q[1]));
        }

        return ret;
    }

private:
    class UF {
    public:
        pair<string,double> find(string x) {
            if (parent.count(x) == 0) {
                parent[x] = {x, 1.0};
            }

            else if (x != parent[x].first) {
                auto root = find(parent[x].first);
                parent[x] = {root.first, root.second * parent[x].second};
            }

            return parent[x];
        }

        // rootA = x / rootX.second = value * y / rootX.second
        // rootB = y / rootY.second
        void connect(string x, string y, double value) {
            auto rootX = find(x);
            auto rootY = find(y);

            if (rootX.first != rootY.first) {
                parent[rootX.first] = {rootY.first, value * rootY.second / rootX.second}; 
            }
        }

        double query(string x, string y) {
            if (parent.count(x) == 0 || parent.count(y) == 0)   return -1.0;
            auto rootX = find(x);
            auto rootY = find(y);

            if (rootX.first != rootY.first) {
                return -1.0;
            }

            return rootX.second / rootY.second;
        }
    private:
        unordered_map<string, pair<string, double>> parent;
    };
};

results matching ""

    No results matching ""