use of catdata.fql.decl.SigExp.Plus in project fql by CategoricalData.
the class SigOps method plus.
private static Quad<SigExp.Const, Const, Const, Fn<Triple<SigExp.Const, Const, Const>, Const>> plus(SigExp.Const a, SigExp.Const b) {
int node_count = 0;
Map<String, String> node_map_1 = new LinkedHashMap<>();
Map<String, String> node_map_2 = new LinkedHashMap<>();
List<Pair<String, String>> a_objs = new LinkedList<>();
List<Pair<String, String>> b_objs = new LinkedList<>();
for (String n : a.nodes) {
node_map_1.put(n, "node" + node_count);
a_objs.add(new Pair<>(n, "node" + node_count));
node_count++;
}
for (String n : b.nodes) {
node_map_2.put(n, "node" + node_count);
b_objs.add(new Pair<>(n, "node" + node_count));
node_count++;
}
List<String> nodes = new LinkedList<>();
nodes.addAll(node_map_1.values());
nodes.addAll(node_map_2.values());
int attr_count = 0;
Map<String, Triple<String, String, String>> attr_map_1 = new LinkedHashMap<>();
Map<String, Triple<String, String, String>> attr_map_2 = new LinkedHashMap<>();
List<Pair<String, String>> a_attrs = new LinkedList<>();
List<Pair<String, String>> b_attrs = new LinkedList<>();
for (Triple<String, String, String> n : a.attrs) {
attr_map_1.put(n.first, new Triple<>("attr" + attr_count, node_map_1.get(n.second), n.third));
a_attrs.add(new Pair<>(n.first, "attr" + attr_count));
attr_count++;
}
for (Triple<String, String, String> n : b.attrs) {
attr_map_2.put(n.first, new Triple<>("attr" + attr_count, node_map_2.get(n.second), n.third));
b_attrs.add(new Pair<>(n.first, "attr" + attr_count));
attr_count++;
}
List<Triple<String, String, String>> attrs = new LinkedList<>();
attrs.addAll(attr_map_1.values());
attrs.addAll(attr_map_2.values());
int edge_count = 0;
Map<String, Triple<String, String, String>> edge_map_1 = new LinkedHashMap<>();
Map<String, Triple<String, String, String>> edge_map_2 = new LinkedHashMap<>();
List<Pair<String, List<String>>> a_arrows = new LinkedList<>();
List<Pair<String, List<String>>> b_arrows = new LinkedList<>();
for (Triple<String, String, String> n : a.arrows) {
edge_map_1.put(n.first, new Triple<>("edge" + edge_count, node_map_1.get(n.second), node_map_1.get(n.third)));
List<String> x = new LinkedList<>();
x.add(node_map_1.get(n.second));
x.add("edge" + edge_count);
a_arrows.add(new Pair<>(n.first, x));
edge_count++;
}
for (Triple<String, String, String> n : b.arrows) {
edge_map_2.put(n.first, new Triple<>("edge" + edge_count, node_map_2.get(n.second), node_map_2.get(n.third)));
List<String> x = new LinkedList<>();
x.add(node_map_2.get(n.second));
x.add("edge" + edge_count);
b_arrows.add(new Pair<>(n.first, x));
edge_count++;
}
List<Triple<String, String, String>> arrows = new LinkedList<>();
arrows.addAll(edge_map_1.values());
arrows.addAll(edge_map_2.values());
List<Pair<List<String>, List<String>>> eqs = new LinkedList<>();
for (Pair<List<String>, List<String>> eq : a.eqs) {
List<String> lhs = new LinkedList<>();
lhs.add(node_map_1.get(eq.first.get(0)));
for (int i = 1; i < eq.first.size(); i++) {
lhs.add(edge_map_1.get(eq.first.get(i)).first);
}
List<String> rhs = new LinkedList<>();
rhs.add(node_map_1.get(eq.second.get(0)));
for (int i = 1; i < eq.second.size(); i++) {
rhs.add(edge_map_1.get(eq.second.get(i)).first);
}
eqs.add(new Pair<>(lhs, rhs));
}
for (Pair<List<String>, List<String>> eq : b.eqs) {
List<String> lhs = new LinkedList<>();
lhs.add(node_map_2.get(eq.first.get(0)));
for (int i = 1; i < eq.first.size(); i++) {
lhs.add(edge_map_2.get(eq.first.get(i)).first);
}
List<String> rhs = new LinkedList<>();
rhs.add(node_map_2.get(eq.second.get(0)));
for (int i = 1; i < eq.second.size(); i++) {
rhs.add(edge_map_2.get(eq.second.get(i)).first);
}
eqs.add(new Pair<>(lhs, rhs));
}
SigExp.Const sig = new SigExp.Const(nodes, attrs, arrows, eqs);
Const inj1 = new Const(a_objs, a_attrs, a_arrows, a, sig);
Const inj2 = new Const(b_objs, b_attrs, b_arrows, b, sig);
Fn<Triple<SigExp.Const, Const, Const>, Const> match = x -> {
SigExp.Const c = x.first;
Const f = x.second;
Const g = x.third;
if (!f.dst.equals(g.dst)) {
throw new RuntimeException("Targets don't agree: " + f.dst + " and " + g.dst);
}
if (!f.src.equals(a)) {
throw new RuntimeException("Source of " + f + " is not " + a);
}
if (!g.src.equals(b)) {
throw new RuntimeException("Source of " + g + "is not " + b);
}
List<Pair<String, String>> objs = new LinkedList<>();
for (String obj_a : a.nodes) {
objs.add(new Pair<>(node_map_1.get(obj_a), lookup(obj_a, f.objs)));
}
for (String obj_b : b.nodes) {
objs.add(new Pair<>(node_map_2.get(obj_b), lookup(obj_b, g.objs)));
}
List<Pair<String, String>> attrs1 = new LinkedList<>();
for (Triple<String, String, String> attr_a : a.attrs) {
attrs1.add(new Pair<>(attr_map_1.get(attr_a.first).first, lookup(attr_a.first, f.attrs)));
}
for (Triple<String, String, String> attr_b : b.attrs) {
attrs1.add(new Pair<>(attr_map_2.get(attr_b.first).first, lookup(attr_b.first, g.attrs)));
}
List<Pair<String, List<String>>> arrows1 = new LinkedList<>();
for (Triple<String, String, String> edge_a : a.arrows) {
arrows1.add(new Pair<>(edge_map_1.get(edge_a.first).first, lookup(edge_a.first, f.arrows)));
}
for (Triple<String, String, String> edge_b : b.arrows) {
arrows1.add(new Pair<>(edge_map_2.get(edge_b.first).first, lookup(edge_b.first, g.arrows)));
}
return new Const(objs, attrs1, arrows1, sig, c);
};
return new Quad<>(sig, inj1, inj2, match);
}
Aggregations