想要改进我的AQL查询(Ideas to improve my AQL query)

编程入门 行业动态 更新时间:2024-10-08 20:32:15
想要改进我的AQL查询(Ideas to improve my AQL query)

在我的图表中,用户连接到许多项目,并且每个项目可以递归地划分为许多子项目。 由于我的项目有特定的排序,我正在考虑这两个选项来建模我的数据:

现在我想创建一个查询来检索给定userID的两个级别的项目。 这个AQL是我的第一次尝试:

for itemId in (for b in board filter b._from == @_from sort b.order return b._to) for item1 in (for t in item filter t._id == itemId return keep(t, '_id', 'title')) return merge(item1, {board: ( for itemId2 in (for b in board filter b._from == item1._id sort b.order return b._to) for t in item filter t._id == itemId2 return keep(t, '_id', 'title') )})

查询工作,它输出如下结果:

[ { "title": "item 1", "_id": "item/41260117498", "board": [ { "title": "item 4", "_id": "item/42205736442" }, { "title": "item 5", "_id": "item/42208423418" } ] }, { "title": "item 2", "_id": "item/41260772858", "board": [] }, { "title": "item 3", "_id": "item/41883233786", "board": [] } ]

这很好,但我觉得我的查询对于这样一个简单的遍历来说是不必要的复杂。 有人可以帮助我创造一个更好的吗?

In my graph, a user is connected to many items and each item can be recursively divided into many sub-items. Since my items have a particular ordering, I'm considering these two options to model my data:

Now I want to create a query to retrieve two levels of items for a given userID. This AQL is my first attempt:

for itemId in (for b in board filter b._from == @_from sort b.order return b._to) for item1 in (for t in item filter t._id == itemId return keep(t, '_id', 'title')) return merge(item1, {board: ( for itemId2 in (for b in board filter b._from == item1._id sort b.order return b._to) for t in item filter t._id == itemId2 return keep(t, '_id', 'title') )})

The query works and it outputs a result like this:

[ { "title": "item 1", "_id": "item/41260117498", "board": [ { "title": "item 4", "_id": "item/42205736442" }, { "title": "item 5", "_id": "item/42208423418" } ] }, { "title": "item 2", "_id": "item/41260772858", "board": [] }, { "title": "item 3", "_id": "item/41883233786", "board": [] } ]

Which is fine, but I feel like my query is unnecessarily complex for such a simple traversal. Could someone help me to create a better one, please?

最满意答案

使用图形数据库的关键是利用它的图形查询功能让它处理边缘,而不是通过手动连接边缘自己完成。

我将演示这种查询的模式匹配遍历 ; 它们可以在引擎盖下透明地处理边缘( _from和_to )的_to 。

首先,您将创建一个图形来配置边缘关系,为简单起见,我们使用匿名图形。 您有边缘收集board和顶点集合user和item 。

首先,您只需运行整个查询即可了解其工作原理,并检查完整结果:

FOR v, e, p IN 1..3 OUTBOUND 'user/andy' board RETURN {v: v, e: e, p: p}

您可以看到只需指定起始节点和边集合board ,它将通过检查边缘找到要自行查询的顶点集合。

现在我们可以添加FILTER来省略我们不喜欢的边和顶点:

FOR v, e, p IN 1..3 OUTBOUND 'user/andy' board FILTER e.title == 'item 2' FILTER p.edges[1].title != 'item 1' RETURN {v: v, e: e, p: p}

该示例包含两个FILTER指令; 一个匹配每个边以使title属性等于"item 2" ,另一个匹配遍历中的第一个边必须包含title "item 1" 。

最后我们使用文档操作来获取我们喜欢的文档部分:

FOR v, e, p IN 1..3 OUTBOUND 'user/andy' board FILTER e.title == 'item 2' RETURN {v: v, e: {title: e.title, _id: e._id}, pathEdgeTitle: p.edges[*].title}

The point in using a graph database is utilize its graph querying capabilities letting it handle the edges, and not to do it on your own by manually joining the edges.

I will demonstrate the pattern matching traversals for such a query; they handle the transision over the edges (_from and _to) transparently under the hood for you.

First you would create a graph to configure your edge relations, we use an anonymous graph for simplicity. You have the edge collection board and the vertex collections user and item.

First you simply let run the whole query to get a feeling for how it works, and inspect the full result:

FOR v, e, p IN 1..3 OUTBOUND 'user/andy' board RETURN {v: v, e: e, p: p}

You see that you only need to specify the start node, and the edge collection board, it will find the vertex collections to query on its own by inspecting the edges.

Now we may add FILTERs to omit edges and vertices that we don't like:

FOR v, e, p IN 1..3 OUTBOUND 'user/andy' board FILTER e.title == 'item 2' FILTER p.edges[1].title != 'item 1' RETURN {v: v, e: e, p: p}

The example contains two FILTER instructions; one is matching each edge to have the title attribute being equal "item 2", the other is matching that the first edge in the traversal has to contain title "item 1".

Finaly we use document manipulation to only get the parts of the documents we like:

FOR v, e, p IN 1..3 OUTBOUND 'user/andy' board FILTER e.title == 'item 2' RETURN {v: v, e: {title: e.title, _id: e._id}, pathEdgeTitle: p.edges[*].title}

更多推荐

本文发布于:2023-07-18 07:39:00,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1157069.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:Ideas   AQL   query   improve

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!