[feature](Nereids): graphSimplifier should compare edge1BeforeEdge2 and edge2BeforeEdge1 (#25416)

This commit is contained in:
谢健
2023-10-17 14:10:21 +08:00
committed by GitHub
parent c4cc6cefda
commit 4d12d8885e
5 changed files with 58 additions and 27 deletions

View File

@ -53,13 +53,13 @@ public class Edge {
private long referenceNodes = LongBitmap.newBitmap();
// record the left child edges and right child edges in origin plan tree
private BitSet leftChildEdges;
private BitSet rightChildEdges;
private final BitSet leftChildEdges;
private final BitSet rightChildEdges;
// record the edges in the same operator
private BitSet curJoinEdges = new BitSet();
private final BitSet curJoinEdges = new BitSet();
// record all sub nodes behind in this operator. It's T function in paper
private Long subTreeNodes;
private final long subTreeNodes;
/**
* Create simple edge.

View File

@ -418,14 +418,18 @@ public class GraphSimplifier {
private SimplificationStep orderJoin(Pair<Statistics, Edge> edge1Before2,
Pair<Statistics, Edge> edge2Before1, int edgeIndex1, int edgeIndex2) {
Edge edge = processMissedEdges(edgeIndex1, edgeIndex2, edge1Before2.second);
Cost cost1Before2 = calCost(edge, edge1Before2.first,
cacheStats.get(edge1Before2.second.getLeftExtendedNodes()),
cacheStats.get(edge1Before2.second.getRightExtendedNodes()));
edge = processMissedEdges(edgeIndex1, edgeIndex2, edge2Before1.second);
Cost cost2Before1 = calCost(edge, edge1Before2.first,
// TODO: Consider miss edges when construct join.
// considering
// a
// / \
// b - c
// when constructing edge_ab before edge_bc. edge_ac should be added on top join
Cost cost1Before2 = calCost(edge1Before2.second, edge1Before2.first,
cacheStats.get(edge1Before2.second.getLeftExtendedNodes()),
cacheStats.get(edge1Before2.second.getRightExtendedNodes()));
Cost cost2Before1 = calCost(edge2Before1.second, edge2Before1.first,
cacheStats.get(edge2Before1.second.getLeftExtendedNodes()),
cacheStats.get(edge2Before1.second.getRightExtendedNodes()));
double benefit = Double.MAX_VALUE;
SimplificationStep step;
// Choose the plan with smaller cost and make the simplification step to replace the old edge by it.
@ -505,10 +509,10 @@ public class GraphSimplifier {
Edge edge2 = graph.getEdge(j);
if (edge1.isSub(edge2)) {
Preconditions.checkArgument(circleDetector.tryAddDirectedEdge(i, j),
String.format("Edge %s violates Edge %s", edge1, edge2));
"Edge %s violates Edge %s", edge1, edge2);
} else if (edge2.isSub(edge1)) {
Preconditions.checkArgument(circleDetector.tryAddDirectedEdge(j, i),
String.format("Edge %s violates Edge %s", edge2, edge1));
"Edge %s violates Edge %s", edge2, edge1);
}
}
}

View File

@ -227,19 +227,20 @@ public class HyperGraph {
edgeB.setRightExtendedNodes(rightRequired);
}
private BitSet subTreeEdges(Edge edge) {
BitSet bitSet = new BitSet();
bitSet.or(subTreeEdges(edge.getLeftChildEdges()));
bitSet.or(subTreeEdges(edge.getRightChildEdges()));
bitSet.set(edge.getIndex());
return bitSet;
private BitSet subTreeEdge(Edge edge) {
long subTreeNodes = edge.getSubTreeNodes();
BitSet subEdges = new BitSet();
edges.stream()
.filter(e -> LongBitmap.isSubset(subTreeNodes, e.getReferenceNodes()))
.forEach(e -> subEdges.set(e.getIndex()));
return subEdges;
}
private BitSet subTreeEdges(BitSet edgeSet) {
BitSet bitSet = new BitSet();
edgeSet.stream()
.mapToObj(i -> subTreeEdges(edges.get(i)))
.forEach(b -> bitSet.or(b));
.mapToObj(i -> subTreeEdge(edges.get(i)))
.forEach(bitSet::or);
return bitSet;
}