Source: https://dev-docs.yueshu.com.cn/v5.3.2/database-gql-reference/variable-definition/table-variable/ Documentation version: v5.3.2 # 表变量 表变量以表格形式存储数据。在悦数图数据库开发版中,表变量主要用于保存查询结果、遍历中间结果,以及驱动批量插入、更新或删除点和边。 本文介绍悦数图数据库开发版中使用的本地表变量。 ## 语法 语法图源码 table_variable_definition table_value_constructor table_expression ```` table_variable_definition ::= 'BINDING'? 'TABLE' table_variable ( ((( '::' | 'TYPED' ) 'BINDING TABLE')? '{' (field_name value_type) (',' (field_name value_type))* '}' ('=' table_value_constructor)? ) | '{' field_name (',' field_name)* '}' '=' table_value_constructor | '=' table_value_constructor ) table_value_constructor ::= table_expression | '{' procedure_body '}' table_expression ::= ( '{' (field_name ':' value_expression) (',' (field_name ':' value_expression))* '}' ) (',' ( '{' (field_name ':' value_expression) (',' (field_name ':' value_expression))* '}' ) )* | ( '(' value_expression (',' value_expression)* ')' ) ( ',' ( '(' value_expression (',' value_expression)* ')' ) )* ```` ## 参数 ### `table_variable` 要定义的表变量的名称。`table_variable`可以是常规标识符或使用反引号(```)包围的分隔标识符。有关标识符的更多信息,请参见[标识符命名规则](https://dev-docs.yueshu.com.cn/v5.3.2/database-gql-reference/overview/keywords-identifiers/)。 ### `field_name` 表中字段的名称。`field_name`必须是一个标识符。有关标识符的更多信息,请参见[标识符命名规则](https://dev-docs.yueshu.com.cn/v5.3.2/database-gql-reference/overview/keywords-identifiers/)。 ### `value_type` 字段所持有的值的数据类型。支持的数据类型包括数值、字符串、布尔值、时间和日期、向量、列表、集合、映射、记录。更多信息,请参见[数据类型](https://dev-docs.yueshu.com.cn/v5.3.2/database-gql-reference/data-types/)。 ### `value_expression` 表中字段的值。`value_expression`必须是一个不依赖于任何变量的表达式。有关值表达式的更多信息,请参见[值表达式](https://dev-docs.yueshu.com.cn/v5.3.2/database-gql-reference/fe/#_6)。 ### `procedure_body` 一个或者一组被执行的 DQL 语句。更多信息,请参见[过程体](https://dev-docs.yueshu.com.cn/v5.3.2/database-gql-reference/procedures/#_3)和 [DQL 语句](https://dev-docs.yueshu.com.cn/v5.3.2/database-gql-reference/dql/)。 ## 成员函数 ### clear() 清除表变量中的所有数据。 #### 函数签名 ```` clear() -> VOID ```` #### 使用说明 只能使用`SET`语句来调用`clear()`函数。更多信息,请参见 [SET](https://dev-docs.yueshu.com.cn/v5.3.2/database-gql-reference/set/)。 ## 示例 以下示例基于[示例数据集](https://dev-docs.yueshu.com.cn/v5.3.2/database-gql-reference/overview/example-dataset/)。 ### 定义表变量时不赋值 ```` ''' TABLE t :: TABLE { a INT, b BOOL, c TYPED STRING, d DOUBLE, e LIST, f RECORD {x INT, y STRING}, g DATE, h VECTOR<3,FLOAT> } FINISH ''' ```` ### 定义表变量时声明字段类型 ```` ''' TABLE t TYPED TABLE { id INT64, name STRING, birthDate DATE } = { id: 10001, name: 'Alice', birthDate: DATE '1990-01-01' }, { id: 10002, name: 'Bob', birthDate: DATE '1991-02-02' }, { id: 10003, name: 'Charlie', birthDate: DATE '1992-03-03' } FOR re IN t RETURN re.id, re.name, re.birthDate ''' ```` 上述语句定义了表变量`t`,并显式声明了表中字段`id`、`name`和`birthDate`的数据类型,同时向表中添加了三行数据。之后,`FOR`子句遍历表变量`t`,并返回字段`id`、`name`和`birthDate`的值。 返回: ```` +-------+---------+--------------+ | re.id | re.name | re.birthDate | +-------+---------+--------------+ | 10001 | Alice | 1990-01-01 | | 10002 | Bob | 1991-02-02 | | 10003 | Charlie | 1992-03-03 | +-------+---------+--------------+ ```` ### 定义表变量时不声明字段类型 ```` ''' TABLE t { id, name, birthDate } = ( 10001, 'Alice', DATE '1990-01-01' ), ( 10002, 'Bob', DATE '1991-02-02' ), ( 10003, 'Charlie', DATE '1992-03-03' ) FOR re IN t RETURN re.id, re.name, re.birthDate ''' ```` 上述语句定义了表变量`t`,未声明其字段`id`、`name`和`birthDate`的数据类型,但在向表中添加数据时指定了各个字段的数据类型。之后,`FOR`子句遍历表变量`t`,并返回字段`id`、`name`和`birthDate`的值。 返回: ```` +-------+---------+--------------+ | re.id | re.name | re.birthDate | +-------+---------+--------------+ | 10001 | Alice | 1990-01-01 | | 10002 | Bob | 1991-02-02 | | 10003 | Charlie | 1992-03-03 | +-------+---------+--------------+ ```` ### 从查询结果定义表变量 #### 从查询推断字段名称和类型 ```` ''' TABLE t = { USE movie MATCH (v:Person) RETURN v.name AS name, v.id AS id ORDER BY name LIMIT 3 } FOR rec IN t RETURN rec.name, rec.id ''' ```` 返回: ```` +------------------+--------+ | rec.name | rec.id | +------------------+--------+ | Aaron Eckhart | 6383 | | Ada Lonati | 162562 | | Adam Alexi-Malle | 20804 | +------------------+--------+ ```` 上述语句通过`MATCH`语句的查询结果定义了表变量`t`。字段名称(`name`、`id`)及其类型从`RETURN`子句的别名中自动推断。 #### 显式指定字段名称 ```` ''' TABLE t { personName, personId } = { USE movie MATCH (v:Person) RETURN v.name, v.id ORDER BY v.name LIMIT 3 } FOR rec IN t RETURN rec.personName, rec.personId ''' ```` 返回: ```` +------------------+--------------+ | rec.personName | rec.personId | +------------------+--------------+ | Aaron Eckhart | 6383 | | Ada Lonati | 162562 | | Adam Alexi-Malle | 20804 | +------------------+--------------+ ```` 上述语句定义了表变量`t`,并显式指定字段名称为`personName`和`personId`。查询返回的`v.name`和`v.id`按顺序映射到指定的字段名称。 #### 显式指定字段名称和类型 ```` ''' TABLE t TYPED TABLE { name STRING, id INT64 } = { USE movie MATCH (v:Person) RETURN v.name, v.id ORDER BY v.name LIMIT 3 } FOR rec IN t RETURN rec.name, rec.id ''' ```` 返回: ```` +------------------+--------+ | rec.name | rec.id | +------------------+--------+ | Aaron Eckhart | 6383 | | Ada Lonati | 162562 | | Adam Alexi-Malle | 20804 | +------------------+--------+ ```` 上述语句定义了表变量`t`,并指定了类型。查询输出必须与声明的类型兼容,否则会报错。 #### 在查询中使用关联变量 ```` ''' VALUE personId = 100 TABLE friends = { USE movie MATCH (f:Person)-[:Act]->(m:Movie) WHERE f.id = personId RETURN f.id AS fid, f.name AS fname } FOR rec IN friends RETURN rec.fid, rec.fname ''' ```` 返回: ```` +---------+----------------+ | rec.fid | rec.fname | +---------+----------------+ | 100 | Scott Speedman | +---------+----------------+ ```` 上述语句首先定义了值变量`personId`,然后定义了表变量`friends`,其查询在`WHERE`子句中引用了`personId`。这样可以使用预先定义的变量进行参数化查询。 ### 清除表变量 ```` ''' TABLE t {id, name} = (10, "new1"), (20, "new2") SET t.clear() FOR rec IN t RETURN rec.id, rec.name ''' ```` 返回: ```` +--------+----------+ | rec.id | rec.name | +--------+----------+ +--------+----------+ ```` ### 使用表变量批量插入点 ```` ''' TABLE t { id, name, birthDate } = ( 10001, 'Alice', DATE '1990-01-01' ), ( 10002, 'Bob', DATE '1991-02-02' ), ( 10003, 'Charlie', DATE '1992-03-03' ) USE movie FOR re IN t INSERT (@Actor {id: re.id, name: re.name, birthDate: re.birthDate}) ''' ```` 上述语句定义了表变量`t`,并遍历表变量的字段,插入点类型为`Actor`的点到图`movie`中。 关于插入操作的更多信息,请参见 [INSERT](https://dev-docs.yueshu.com.cn/v5.3.2/database-gql-reference/dml/insert/)。 ### 使用表变量批量插入点和边 ```` ''' TABLE t { actor_id, movie_id, movie_name } = ( 10001 , 20001, 'Movie1' ), ( 10002 , 20002, 'Movie2' ), ( 10003 , 20003, 'Movie3' ) USE movie FOR re IN t MATCH (a@Actor) WHERE a.id = re.actor_id INSERT (a)-[@Act]->(@Movie {id: re.movie_id, name: re.movie_name}) ''' ```` 上述语句定义了表变量`t`,并遍历表变量将数据插入到图`movie`中。该语句基于表变量的字段`actor_id`匹配点类型为`Actor`的点,并基于字段`movie_id`和`movie_name`的值插入点类型为`Movie`的点,并在这些点之间插入边。 ### 使用表变量批量更新点 ```` ''' TABLE t { id, new_name } = ( 10001, 'Alice_renamed' ), ( 10002, 'Bob_renamed' ), ( 10003, 'Charlie_renamed' ) USE movie FOR re IN t MATCH (a@Actor) WHERE a.id = re.id SET a.name = re.new_name ''' ```` 上述语句定义了表变量`t`,并基于表变量的字段`id`匹配点类型为`Actor`的点。然后,根据表变量的字段`new_name`更新匹配到的点的属性`name`。 关于更新操作的更多信息,请参见 [SET](https://dev-docs.yueshu.com.cn/v5.3.2/database-gql-reference/dml/set/)。 ### 使用表变量批量删除点 ```` ''' TABLE t { id } = ( 10001 ), ( 10002 ), ( 10003 ) USE movie FOR re IN t MATCH (a@Actor) WHERE a.id = re.id DETACH DELETE a ''' ```` 上述语句定义了表变量`t`,并基于表变量的字段`id`匹配点类型为`Actor`的点。然后,删除匹配到的点及与其连接的所有边。 关于删除操作的更多信息,请参见 [DELETE](https://dev-docs.yueshu.com.cn/v5.3.2/database-gql-reference/dml/delete/)。 ### 在临时图中使用表变量 以下示例基于 [CREATE TEMPORARY GRAPH](https://dev-docs.yueshu.com.cn/v5.3.2/database-gql-reference/ddl/graph-projection/create/) 中创建的临时图`#movie_temporary_graph`。 ```` ''' USE #movie_temporary_graph { TABLE result_table TYPED TABLE { id INT, name STRING } MATCH (a@Movie) PER NODE (a) { EXPORT a.id AS id, a.name AS name INTO result_table } FOR r IN result_table RETURN r.id AS id, r.name AS name LIMIT 3 } ''' ```` 返回: ```` +-----+------------+ | id | name | +-----+------------+ | 572 | Next Door | | 427 | My Uncle | | 269 | Breathless | +-----+------------+ ```` 上述语句在已有的临时图`#movie_temporary_graph`中定义表变量`result_table`。该表变量通过匹配计算语句查询图中的`Movie`点,并将点的`id`和`name`字段导出到`result_table`中。最后,使用`FOR`子句遍历`result_table`并返回3条记录。