-
Notifications
You must be signed in to change notification settings - Fork 0
[COR-78] Add limited-traversal query on a binary tree with one supernode #69
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
+179
−105
Merged
Changes from all commits
Commits
Show all changes
5 commits
Select commit
Hold shift + click to select a range
566ff5f
Add limited-traversal query on a binary tree with one supernode
jvolmer 3f5914d
Add traversal without limit
jvolmer 225f3a8
Fix unstable traversal tests
jvolmer 5dc03e3
Implement PR suggestions
jvolmer e806add
Fix single server
jvolmer File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file was deleted.
Oops, something went wrong.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,134 @@ | ||
| const rand = require("internal").rand; | ||
|
|
||
| function makeRandomString(l) { | ||
| const d = rand(); | ||
| let r = rand(); | ||
| let s = "x"; | ||
| for (let i = 0; i < l; ++i) { | ||
| s += r; | ||
| r += d; | ||
| } | ||
| return s; | ||
| } | ||
|
|
||
| function numberOfDbservers() { | ||
| let health = db._connection.GET("/_admin/cluster/health"); | ||
| if (health.error) { | ||
| return 1; | ||
| } else { | ||
| return Object.values(health.Health).filter(item => item.Role == "DBServer").length; | ||
| } | ||
| } | ||
|
|
||
| function createGraph(graphName, vertexCollName, edgeCollName) { | ||
| let graph = require("@arangodb/general-graph"); | ||
| try { | ||
| graph._drop(graphName, true); | ||
| } | ||
| catch { | ||
| } | ||
| graph._create(graphName, [graph._relation(edgeCollName, [vertexCollName], [vertexCollName])], [], {numberOfShards: numberOfDbservers()}); | ||
| } | ||
|
|
||
| function makeKey(i) { | ||
| return "S" + (i % 3) + ":K" + i; | ||
| } | ||
|
|
||
| // creates a binary tree where every vertex includes one megabyte of data | ||
| // | ||
| // The following AQL query and its performance could be of interest: | ||
| // | ||
| // FOR v IN 0..6 OUTBOUND "V/S1:K1" GRAPH "G" | ||
| // RETURN v.data | ||
| // | ||
| // This traverses the whole graph starting from the root but retrieves only | ||
| // a tiny part of the vertex data. This tests the 3.10 feature of | ||
| // traversal projections. You can see that it does this from this explain | ||
| // output for the above query: | ||
| // | ||
| // Query String (58 chars, cacheable: true): | ||
| // FOR v IN 0..6 OUTBOUND "V/S1:K1" GRAPH "G" | ||
| // RETURN v.smallData | ||
| // | ||
| // Execution plan: | ||
| // Id NodeType Site Est. Comment | ||
| // 1 SingletonNode COOR 1 * ROOT | ||
| // 2 TraversalNode COOR 64 - FOR v /* vertex (projections: `data`) */ IN 0..6 /* min..maxPathDepth */ OUTBOUND 'V/S1:K1' /* startnode */ GRAPH 'G' | ||
| // 3 CalculationNode COOR 64 - LET #3 = v.`smallData` /* attribute expression */ | ||
| // 4 ReturnNode COOR 64 - RETURN #3 | ||
| // | ||
| // In the line with Id 2 you can see that the TraversalNode uses a projection to the field `smallData`. | ||
| function makeTreeWithLargeData(graphName, vertexCollName, edgeCollName, depth) { | ||
| createGraph(graphName, vertexCollName, edgeCollName); | ||
| let V = db._collection(vertexCollName); | ||
| let E = db._collection(edgeCollName); | ||
|
|
||
| // create vertices | ||
| let klumpen = {}; | ||
| for (let i = 0; i < 1000; ++i) { | ||
| klumpen["K"+i] = makeRandomString(1024); | ||
| } | ||
| for (let i = 1; i <= 2 ** depth - 1; ++i) { | ||
| let v = klumpen; | ||
| v.smallData = "D"+i; | ||
| v.smart = "S"+(i % 3); | ||
| v._key = makeKey(i); | ||
| V.insert(v); | ||
| print("Have created", i, "vertices out of", 2 ** depth - 1); | ||
| } | ||
|
|
||
| // make a binary tree from these vertices | ||
| for (let i = 1; i <= 2 ** (depth - 1) - 1; ++i) { | ||
| let e = { _from: vertexCollName + "/" + makeKey(i), | ||
| _to: vertexCollName + "/" + makeKey(2 * i)}; | ||
| E.insert(e); | ||
| e = { _from: vertexCollName + "/" + makeKey(i), | ||
| _to: vertexCollName + "/" + makeKey(2 * i + 1)}; | ||
| E.insert(e); | ||
| } | ||
| } | ||
|
|
||
| // creates a binary tree with vertex 2 beeing a supernode | ||
| // 1 | ||
| // / \ | ||
| // 3 2 with additional superNodeSize neighbours | ||
| // / \ / \ | ||
| // 7 6 5 4 | ||
| // ... | ||
| function makeTreeWithSupernode(graphName, vertexCollName, edgeCollName, depth, superNodeSize) { | ||
| createGraph(graphName, vertexCollName, edgeCollName); | ||
| let V = db._collection(vertexCollName); | ||
| let E = db._collection(edgeCollName); | ||
|
|
||
| // Add 2^depth - 1 vertices for tree and additionally superNodeSize vertices | ||
| let docs = [] | ||
| for (let i = 1; i <= 2**depth-1+superNodeSize; ++i) { | ||
| docs.push({data: "D"+i, smart: "S"+(i%3), _key: makeKey(i)}); | ||
| } | ||
| V.insert(docs); | ||
|
|
||
| // make a binary tree from the first 2^depth - 1 vertices | ||
| docs = []; | ||
| for (let i = 1; i <= 2 ** (depth - 1) - 1; ++i) { | ||
| docs.push({ _from: vertexCollName + "/" + makeKey(i), | ||
| _to: vertexCollName + "/" + makeKey(2 * i)}); | ||
| docs.push({ _from: vertexCollName + "/" + makeKey(i), | ||
| _to: vertexCollName + "/" + makeKey(2 * i + 1)}); | ||
|
|
||
| } | ||
| E.insert(docs); | ||
|
|
||
| // make vertex 2 a supernode | ||
| if (depth > 1) { | ||
| docs = []; | ||
| let key = makeKey(2); | ||
| for (let j=1; j <= superNodeSize; j++) { | ||
| docs.push({_from: vertexCollName + "/" + key, _to: vertexCollName + "/" + (2**depth - 1+j)}); | ||
| } | ||
| E.insert(docs); | ||
| } | ||
| } | ||
|
|
||
| exports.numberOfDbservers = numberOfDbservers; | ||
| exports.makeTreeWithLargeData = makeTreeWithLargeData; | ||
| exports.makeTreeWithSupernode = makeTreeWithSupernode; |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.