输出语句以及文件对象

PRINT语句(第二版API)

PRINT语句用于输出数据。 每次执行PRINT语句,系统都会向结果数组添加一个JSON对象,该结果数组将成为查询输出的一部分。 任何允许存在查询主体层语句的地方都可以使用PRINT语句。

每个PRINT语句内都是一系列表达式,用于定义输出的内容。 我们还可以选择WHERE子句过滤输出结果。 如果某个WHERE子句的条件检查为假,则在最终结果中排除对应的内容。

每个printExpr为PRINT语句的JSON对象提供一个键值对。 我们还可以选择AS子句来配置对应的键,从而覆盖默认键(下例中详述)。

printExpr可能是下列内容之一:

  1. 文字值

  2. 全局或局部变量(包括VERTEX和EDGE变量)

  3. 顶点变量的一个属性,例如Person.name

  4. 全局累积器

  5. 包含上述所有项目的一个表达式。以下运算符可以被使用:

    数学运算符

    算术: + - * / . % 比特: << >> & |

    字符串

    字符串连接: +

    集合

    并集 交集 集合相减

  6. 括号可用于设定运算优先顺序。

  7. 一个顶点集变量

  8. 一个顶点表达式的集合vExprSet(仅当输出API版本设定为v2的时候有效。顶点表达式的集合下文有详述。)

JSON 格式: 键

如果选择在printExpr中添加AS name子句,则用name命名JSON输出的键名。 否则,则以下述规则确定键名:如果表达式只是单个变量(如局部变量,全局变量,全局累加器或顶点集变量),则键名就是变量名称。 若该键是顶点表达式集,则键名是顶点集变量名。 若键是整个表达式,则该键为一个字符串。

JSON 格式: 值

每种数据类型都有不同的输出格式。

  • 简单的数字,字符串和布尔数据类型遵循JSON标准。

  • 列表,集合,包和数组打印为JSON数组(例如方括号中的一组数据)。

  • 映射和元组作为JSON对象打印(例如,用大括号括起来一组的键值对)。

  • 顶点和边包含自定义JSON对象,如下所示。

  • 顶点集变量被视为一系列顶点。

  • 累加器输出格式由累加器的返回值类型决定。 例如,AvgAccum输出DOUBLE值,BitwiseAndAccum输出INT值。 对于容器累加器,只需考虑输出是列表,集合,包还是映射。

    • ListAccum,SetAccum,BagAccum,ArrayAccum:列表

    • MapAccum:映射

    • HeapAccum,GroupByAccum:一系列元组

输出值为顶点(当该顶点不是一个顶点集变量的成员时)

以字符串方式输出顶点id:

顶点(当该顶点不是一个顶点集变量的成员时)的输出值格式

输出值为边

当输出值为边时的输出格式

当输出值为列表, Set或者Bag时的输出格式

输出值为元组

输出值为顶点集变量

顶点表达式集合(Vertex Expression Set)

顶点表达式集合是作用于一个顶点集合的每一个顶点的一组表达式,它用于指明每个顶点的所需要显示的属性。

理解这一点的最简单方法如下:先考虑只有一项的集合,然后再考虑含有多项的集合。例如,下面的查询中 C是一个顶点集变量,它包含了所有的公司顶点(company vertex)组成的集合。 此外,每个顶点都有一个附属于顶点的累加器@count。

如果我们打印输出完整的顶点集,则每个顶点的“属性”会包含三个字段:“id”,“country”和“@count”。现在,假设我们带入一些简单的顶点表达式集:

PRINT C[C.country]

打印出顶点集变量C,但“属性”中仅包含“country”字段,其它两个省略

PRINT C[C.@count]

打印出顶点集变量C,但“属性”中仅包含“@count”字段,其它两个省略

PRINT C[C.id, C.@count]

打印出顶点集变量C,但“属性”中仅包含“id”和“@count”两个字段。

PRINT C[C.id+"_ex", C.@count+1]

打印出顶点集变量C,但“属性”被限制为:

  • 一个字段,字段由每个顶点的id加后缀“_ex”组成。

  • 另一个字段,该字段由@count的值加1得到。注意:@count本身的值并没有改变,只是显示的值递增而已。

最后一个示例演示了一个顶点表达式集的一般格式:

顶点表达式集以顶点集变量的名称开头,然后是一系列包含在方括号中的属性表达式。 每个属性表达式都遵循之前 “PRINT表达式”中的规则。 也就是说,每个属性表达式可以指代当前顶点的一个或多个属性,或附属于该顶点的累加器,或者是文字,或局部或全局的变量以及累加器。 所有可用的运算符(用于数字,字符串或集合操作)都与前文中提到的相同。

顶点表达式集的“键”是顶点集变量的名称。

顶点表达式集的“值”是修改后的顶点集变量,其中每个顶点的默认的“属性”值被替换为一组键值对,这些键值对由PRINT表达式中的一系列属性表达式给出。

下面的示例包括了上述所有情况。

打印成一个CSV格式的文件对象

除了以JSON格式打印输出我们想要的数据之外,还可以打印成以逗号作为分隔符的CSV格式文件(FILE对象)。 如果要这么做,请在PRINT语句的末尾添加关键字TO_CSV,并在它之后注明文件对象的名称:

每次执行PRINT语句都会在文件对象中附加一个新的行。 如果PRINT语句中包含多个表达式,则输出的值与值之间用逗号分隔。 如果表达式得到的结果值为一个集合或列表,则集合内部的值由单个空格分隔。 相较于JSON, CSV的格式更加简单,所以TO_CSV的功能仅支持具有简单一维或二维结构的数据。

将CSV文件数据打印到一个常规文件(不建议使用)

除了可以将CSV输出打印到文件对象外,也可以直接将数据写入常规文件。

下表详述了TO_CSV <文件对象>与TO_CSV <文件路径>之间的差异。

FILE println语句

有两种方法将运算结果打印到文件中,除了上文提到的TO_CSV方法外,还可以使用FILE println语句

println是文件对象变量的一个方法(或称为函数)。 println语句可以在查询主体层语句中使用,也可以在DML子句中使用(例如在SELECT语句的ACCUM子句中使用)。 每次调用println时,它都会先向文件对象添加一行新的值,然后再将其更新到相应的文件中。

println函数可以完成PRINT语句的大多数功能。 但请注意,这其中不包括顶点表达式集(vExprSet)。 如果println语句有一系列表达式需要打印,则它会生成一个以逗号分隔的值的列表。 如果一个表达式引用了列表或集合,则输出将是由空格分隔的值的列表,这与TO_CSV生成的格式是相同的。

在这个示例中,所有的PRINT语句中都选用了TO_CSV选项,所以这个例子中并没有JSON的输出。

这种情况下,所有的输出都是文件对象。 在此查询的定义中,页脚行(footer)是最后一个文件对象语句。但是SELECT语句中的println语句有可能被延迟,在页脚行之后打印。

以参数(Parameter)形式传递文件对象

一个文件对象可以从某个查询传递到子查询,同时该子查询也可以写入文件对象。

LOG语句

LOG语句是另一种输出方法。它以一个函数的形式工作,并输出信息到一个日志文件。

LOG语句的第一个参数是一个布尔值,用于启用或禁用日志记录功能。 通过这个参数,我们可以轻松地打开或关闭日志记录,以便进行调试等用途。 在该参数之后,是一个或多个表达式(以逗号分隔)。系统通过计算这个表达式并得到结果,最终输出到日志文件。

PRINT语句只能用作查询主体层,但LOG语句不同,它既可以用于查询主体语句中,也可以用于DML子句。

信息被记录在GPE的日志文件中。 如果想要在查询完成后找到日志文件,请打开Linux shell并使用命令“gadmin log gpe”。 输出的结果可能会包含多个日志文件名; 其中以“INFO”结尾的那个是我们要的文件。 随后,请在此文件中搜索“UDF_”。

RETURN语句

RETURN语句将子查询生成的数据传递回调用该子查询的母查询。为了将一个查询用作子查询,其初始CREATE QUERY语句必须包含RETURNS子句,并且其正文必须以RETURN语句结束。 RETURNS子句只允许包含一种类,因此RETURN语句只能返回一个结果。返回的结果必须与RETURNS子句指示的类型相同。必须在相应的超级查询之前创建子查询。必须在母查询的同一个INSTALL QUERY命令之前或之中安装子查询。

返回类型可以是任何基本类或任何累加器类,但GroupByAccum累加器和包含任何元组类型的累加器除外。出于确定返回类型的目的,SetAccum等效于Set,而BagAccum等同于Bag。如果在RETURNS子句中使用SET <VERTEX <type>>或SetAccum<VERTEX <type>>(<type>是可选的),则可以返回一个顶点集变量。

另请参见 - 查询和函数。