Skip to content

Commit 6de5e32

Browse files
committed
New Problem Solution -"1766. Tree of Coprimes"
1 parent b6ae9de commit 6de5e32

File tree

2 files changed

+124
-0
lines changed

2 files changed

+124
-0
lines changed

README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ LeetCode
4040
|1770|[Maximum Score from Performing Multiplication Operations](https://leetcode.com/problems/maximum-score-from-performing-multiplication-operations/) | [C++](./algorithms/cpp/maximumScoreFromPerformingMultiplicationOperations/MaximumScoreFromPerformingMultiplicationOperations.cpp)|Medium|
4141
|1769|[Minimum Number of Operations to Move All Balls to Each Box](https://leetcode.com/problems/minimum-number-of-operations-to-move-all-balls-to-each-box/) | [C++](./algorithms/cpp/minimumNumberOfOperationsToMoveAllBallsToEachBox/MinimumNumberOfOperationsToMoveAllBallsToEachBox.cpp)|Medium|
4242
|1768|[Merge Strings Alternately](https://leetcode.com/problems/merge-strings-alternately/) | [C++](./algorithms/cpp/mergeStringsAlternately/MergeStringsAlternately.cpp)|Easy|
43+
|1766|[Tree of Coprimes](https://leetcode.com/problems/tree-of-coprimes/) | [C++](./algorithms/cpp/treeOfCoprimes/TreeOfCoprimes.cpp)|Hard|
4344
|1765|[Map of Highest Peak](https://leetcode.com/problems/map-of-highest-peak/) | [C++](./algorithms/cpp/mapOfHighestPeak/MapOfHighestPeak.cpp)|Medium|
4445
|1764|[Form Array by Concatenating Subarrays of Another Array](https://leetcode.com/problems/form-array-by-concatenating-subarrays-of-another-array/) | [C++](./algorithms/cpp/formArrayByConcatenatingSubarraysOfAnotherArray/FormArrayByConcatenatingSubarraysOfAnotherArray.cpp)|Medium|
4546
|1763|[Longest Nice Substring](https://leetcode.com/problems/longest-nice-substring/) | [C++](./algorithms/cpp/longestNiceSubstring/LongestNiceSubstring.cpp)|Easy|
Lines changed: 123 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,123 @@
1+
// Source : https://leetcode.com/problems/tree-of-coprimes/
2+
// Author : Hao Chen
3+
// Date : 2021-04-01
4+
5+
/*****************************************************************************************************
6+
*
7+
* There is a tree (i.e., a connected, undirected graph that has no cycles) consisting of n nodes
8+
* numbered from 0 to n - 1 and exactly n - 1 edges. Each node has a value associated with it, and the
9+
* root of the tree is node 0.
10+
*
11+
* To represent this tree, you are given an integer array nums and a 2D array edges. Each nums[i]
12+
* represents the i^th node's value, and each edges[j] = [uj, vj] represents an edge between nodes uj
13+
* and vj in the tree.
14+
*
15+
* Two values x and y are coprime if gcd(x, y) == 1 where gcd(x, y) is the greatest common divisor of
16+
* x and y.
17+
*
18+
* An ancestor of a node i is any other node on the shortest path from node i to the root. A node is
19+
* not considered an ancestor of itself.
20+
*
21+
* Return an array ans of size n, where ans[i] is the closest ancestor to node i such that nums[i] and
22+
* nums[ans[i]] are coprime, or -1 if there is no such ancestor.
23+
*
24+
* Example 1:
25+
*
26+
* Input: nums = [2,3,3,2], edges = [[0,1],[1,2],[1,3]]
27+
* Output: [-1,0,0,1]
28+
* Explanation: In the above figure, each node's value is in parentheses.
29+
* - Node 0 has no coprime ancestors.
30+
* - Node 1 has only one ancestor, node 0. Their values are coprime (gcd(2,3) == 1).
31+
* - Node 2 has two ancestors, nodes 1 and 0. Node 1's value is not coprime (gcd(3,3) == 3), but node
32+
* 0's
33+
* value is (gcd(2,3) == 1), so node 0 is the closest valid ancestor.
34+
* - Node 3 has two ancestors, nodes 1 and 0. It is coprime with node 1 (gcd(3,2) == 1), so node 1 is
35+
* its
36+
* closest valid ancestor.
37+
*
38+
* Example 2:
39+
*
40+
* Input: nums = [5,6,10,2,3,6,15], edges = [[0,1],[0,2],[1,3],[1,4],[2,5],[2,6]]
41+
* Output: [-1,0,-1,0,0,0,-1]
42+
*
43+
* Constraints:
44+
*
45+
* nums.length == n
46+
* 1 <= nums[i] <= 50
47+
* 1 <= n <= 10^5
48+
* edges.length == n - 1
49+
* edges[j].length == 2
50+
* 0 <= uj, vj < n
51+
* uj != vj
52+
******************************************************************************************************/
53+
54+
class Solution {
55+
private:
56+
// Euclidean algorithm
57+
// https://en.wikipedia.org/wiki/Euclidean_algorithm
58+
int gcd(int a, int b) {
59+
while (a != b ) {
60+
if (a > b ) a -= b;
61+
else b -= a;
62+
}
63+
return a;
64+
}
65+
void print(vector<int>& v, int len, vector<int>& nums){
66+
cout << "[";
67+
for(int i=0; i< len; i++) {
68+
cout << v[i] <<"("<< nums[v[i]]<<"), ";
69+
}
70+
cout << v[len] <<"("<<nums[v[len]]<<")]"<< endl;
71+
}
72+
73+
public:
74+
vector<int> getCoprimes(vector<int>& nums, vector<vector<int>>& edges) {
75+
unordered_map<int, vector<int>> graph;
76+
for(auto& edge : edges) {
77+
graph[edge[0]].push_back(edge[1]);
78+
graph[edge[1]].push_back(edge[0]);
79+
}
80+
81+
int n = nums.size();
82+
vector<int> result(n, -1);
83+
84+
vector<int> path(n, -1);
85+
path[0] = 0;
86+
87+
// primePos[num] = {position, level};
88+
vector<vector<pair<int, int>>> primePos(51, vector<pair<int, int>>());
89+
90+
getCoprimesDFS(-1, 0, nums, graph, path, 0, primePos, result);
91+
92+
return result;
93+
}
94+
95+
void getCoprimesDFS(int parent, int root,
96+
vector<int>& nums,
97+
unordered_map<int, vector<int>>& graph,
98+
vector<int>& path, int pathLen,
99+
vector<vector<pair<int, int>>>& primePos,
100+
vector<int>& result) {
101+
102+
int max_level = -1;
103+
// find the previous closest prime
104+
for(int n = 0; n < primePos.size(); n++) {
105+
auto& pos = primePos[n];
106+
// no position || not co-prime
107+
if ( pos.size() <=0 || gcd(nums[root], n) != 1) continue;
108+
if (pos.back().second > max_level && pos.back().first != root) {
109+
max_level = pos.back().second;
110+
result[root] = pos.back().first;
111+
}
112+
113+
}
114+
115+
primePos[nums[root]].push_back({root, pathLen});
116+
for (auto& child : graph[root]) {
117+
if (child == parent) continue; // don't go back
118+
path[pathLen+1] = child; // for debug
119+
getCoprimesDFS(root, child, nums, graph, path, pathLen + 1, primePos, result);
120+
}
121+
primePos[nums[root]].pop_back();
122+
}
123+
};

0 commit comments

Comments
 (0)