Introduction to the problem:
They give me recipes for creating items. The recipe is in the following format: {element that is being crafter}: {list of elements, that is needed}. Before I can create an element x, I need to know how to create the elements from which it is made. So I want to find in which order I need to study recipes.
For valid input, like everything that works:
{
"F1: F2 F3 F4", "F5: F6 F4", "F6: F7 F8 F4", "F2: F3 F8 F4", "F8: F4",
"F9: F4", "F7: F4", "F10: F7 F4", "F11: F4", "F4:", "F3: F6"
}
[F4, F7, F8, F6, F3, F2, F1, F5, F9, F10, F11]
The problem is that the task is more complicated. From time to time, I have some recipes that are missing or invalid. EXAMPLE invalid input: { "F1: F2", "F2: F1" }.
Code example:
mp , , labels - mp, result - . empty, .
private void getArray(HashMap<String, ArrayList<String>> mp,
ArrayList<String> result, ArrayList<String> labels) {
for (String a : labels) {
if (mp.get(a) != null)
for (String label : mp.get(a))
getArray(mp, result, label);
if (!result.contains(a))
result.add(a);
}
}
private void getArray(HashMap<String, ArrayList<String>> mp,
ArrayList<String> result, String label) {
if (result.contains(label))
return;
if (mp.get(label) == null) {
result.add(label);
return;
}
for (String l : mp.get(label))
getArray(mp, result, l);
if (!result.contains(label))
result.add(label);
}
.
Google, , :
public static <T> ArrayList<T> tSort(java.util.Map<T, ArrayList<T>> g)
throws Exception
{
java.util.ArrayList<T> L = new ArrayList<T>(g.size());
java.util.Queue<T> S = new java.util.concurrent.LinkedBlockingDeque<T>();
java.util.HashSet<T> V = new java.util.HashSet<T>(),
P = new java.util.HashSet<T>();
P.addAll(g.keySet());
T n;
for (T t : P)
if (g.get(t) == null || g.get(t).isEmpty())
S.add(t);
while (!S.isEmpty()) {
if (V.add(n = S.poll()))
L.add(n);
for (T t : g.keySet())
if (g.get(t) != null && !g.get(t).isEmpty() && !V.contains(t)
&& V.containsAll(g.get(t)))
S.add(t);
}
if (L.containsAll(P))
return L;
StringBuilder sb = new StringBuilder(
"\nInvalid DAG: a cyclic dependency detected :\n");
for (T t : P)
if (!L.contains(t))
sb.append(t).append(" ");
throw new Exception(sb.append("\n").toString());
}
public static <T> void tSortFix(java.util.Map<T, ArrayList<T>> g) {
java.util.ArrayList<T> tmp;
java.util.HashSet<T> P = new java.util.HashSet<T>();
P.addAll(g.keySet());
for (T t : P)
if (g.get(t) != null || !g.get(t).isEmpty()) {
(tmp = g.get(t)).remove(t);
for (T m : tmp)
if (!P.contains(m))
g.put(m, new ArrayList<T>(0));
}
}