

本文属于机器翻译版本。若本译文内容与英语原文存在差异，则一律以英文原文为准。

# 支持的 SQL 和 PPL 命令
<a name="direct-query-supported-commands"></a>

OpenSearch SQL 和 OpenSearch 管道处理语言 (PPL) 是用于查询、分析和处理 L CloudWatch ogs Insights 和 Secur OpenSearch ity Lake 中数据的语言。您可以在 D OpenSearch iscover 中使用 OpenSearch SQ OpenSearch L 和 PPL 来查询 CloudWatch 日志、Amazon S3 或安全湖中的数据。 CloudWatch Logs Insights 还支持 OpenSearch PPL 和 OpenSearch SQL 查询语言，此外还支持 Logs Insights QL（一种专门用于分析日志的查询语言）。 CloudWatch 
+ **OpenSearch SQ** OpenSearch L：如果你习惯使用关系数据库，SQL 提供了一个熟悉的选项。 OpenSearch SQL 提供了 SQL 功能的子集，使其成为执行临时查询和数据分析任务的理想选择。使用 OpenSearch SQL，你可以使用 SELECT、FROM、WHERE、GROUP BY、HAVING 等命令以及 SQL 中提供的各种其他 SQL 命令和函数。您可以 JOINs 跨表（或日志组）执行，使用子查询关联表（或日志组）之间的数据，并使用丰富的 JSON、数学、字符串、条件和其他 SQL 函数集对日志和安全数据进行强有力的分析。
+ **OpenSearch PPL（管道处理语言）：使用 OpenSearch PPL，您可以使用 piped**-together 命令检索、查询和分析数据，从而更容易理解和撰写复杂的查询。其语法基于 Unix 管道，支持通过命令链实现数据的转换与处理。使用 PPL，您可以筛选和聚合数据，并使用子查询 JOINs、LOOKUP 等命令以及丰富的数学、字符串、日期、条件和其他函数进行分析。

尽管 OpenSearch PPL 和 OpenSearch SQL 查询语言中的大多数命令在 CloudWatch 日志中都很常见 OpenSearch，但每种服务支持哪组命令和函数仍存在一些差异。有关更多信息，请参阅后续页面上的表。

****
+ [支持 OpenSearch 的 SQL 命令和函数](supported-directquery-sql.md)
  + [为使用 OpenSearch SQL 的 “ CloudWatch 日志见解” 用户提供的更多信息](supported-directquery-sql.md#supported-sql-for-multi-log-queries)
  + [通用 SQL 限制](supported-directquery-sql.md#general-sql-restrictions)
+ [支持的 PPL 命令](supported-ppl.md)
  + [为使用 OpenSearch PPL 的 CloudWatch Logs Insights 用户提供的其他信息](supported-ppl.md#supported-ppl-for-cloudwatch-users)

# 支持 OpenSearch 的 SQL 命令和函数
<a name="supported-directquery-sql"></a>

以下参考表显示了 D OpenSearch iscover 中支持哪些 SQL 命令来查询 Amazon S3、Security Lake 或 CloudWatch 日志中的数据，以及 Logs Insights 中 CloudWatch 支持哪些 SQL 命令。L CloudWatch ogs Insights 中支持的 SQL 语法与 OpenSearch Discover 中支持的 SQL 语法相同，在下表中被称为 CloudWatch 日志。 CloudWatch 

**注意**  
OpenSearch 还支持 SQL，用于查询已提取 OpenSearch并存储在索引中的数据。此 SQL 方言不同于直接查询中使用的 SQL，在[索引上被称为 OpenSearch SQL](https://opensearch.org/docs/latest/search-plugins/sql/sql/index/)。

**Topics**
+ [

## 命令
](#supported-sql-data-retrieval)
+ [

## 函数
](#supported-sql-functions)
+ [

## 通用 SQL 限制
](#general-sql-restrictions)
+ [

## 为使用 OpenSearch SQL 的 “ CloudWatch 日志见解” 用户提供的更多信息
](#supported-sql-for-multi-log-queries)

## 命令
<a name="supported-sql-data-retrieval"></a>

**注意**  
在示例命令列中，根据需要替换 `<tableName/logGroup>`，具体取决于您要查询的数据来源。  
命令示例：`SELECT Body , Operation FROM <tableName/logGroup>`
如果要查询 Amazon S3 或 Security Lake，则使用：`SELECT Body , Operation FROM table_name`
如果您要查询 CloudWatch 日志，请使用：`SELECT Body , Operation FROM `LogGroupA``


| 命令 | 说明 | CloudWatch 日志 | Amazon S3 | 安全湖 |  命令示例 | 
| --- | --- | --- | --- | --- | --- | 
|  [SELECT 子句](#supported-sql-select)  |  显示预测值。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    method,<br />    status <br />FROM <br />    <tableName/logGroup></pre>  | 
| [WHERE 子句](#supported-sql-where) |  根据提供的字段条件筛选日志事件。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    * <br />FROM <br />    <tableName/logGroup><br />WHERE <br />    status = 100</pre>  | 
| [GROUP BY 子句](#supported-sql-group-by) |  根据类别对日志事件进行分组，并根据统计数据计算平均值。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    method,<br />    status,<br />    COUNT(*) AS request_count,<br />    SUM(bytes) AS total_bytes <br />FROM <br />    <tableName/logGroup> <br />GROUP BY <br />    method, <br />    status</pre>  | 
| [HAVING 子句](#supported-sql-having) |  根据分组条件筛选结果。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    method,<br />    status,<br />    COUNT(*) AS request_count,<br />    SUM(bytes) AS total_bytes <br />FROM <br />    <tableName/logGroup> <br />GROUP BY <br />    method,<br />    status<br />HAVING <br />    COUNT(*) > 5</pre>  | 
| [ORDER BY 子句](#supported-sql-order-by) |  根据顺序子句中的字段对结果进行排序。您可以按降序或升序进行排序。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    * <br />FROM <br />    <tableName/logGroup> <br />ORDER BY <br />    status DESC</pre>  | 
|  [JOIN 子句](#supported-sql-join)  ( `INNER` \$1 `CROSS` \$1 `LEFT` `OUTER` )  |  根据共同字段合并两个表的结果。  |  支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg)（合并必须使用 `Inner` 和 `Left Outer` 关键字；SELECT 语句中仅支持一个 JOIN 操作）  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg)（必须使用 Inner、Left Outer 和 Cross 关键字进行合并） | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg)（必须使用 Inner、Left Outer 和 Cross 关键字进行合并） |  <pre>SELECT <br />    A.Body,<br />    B.Timestamp<br />FROM <br />    <tableNameA/logGroupA> AS A <br />INNER JOIN <br />    <tableNameB/logGroupB> AS B <br />    ON A.`requestId` = B.`requestId`</pre>  | 
| [LIMIT 子句](#supported-sql-limit) |  将结果限制为前 N 行。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    * <br />FROM <br />    <tableName/logGroup> <br />LIMIT <br />    10</pre>  | 
| [CASE 子句](#supported-sql-case) | 评估条件，并在满足第一个条件时返回一个值。 | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT<br />    method,<br />    status,<br />    CASE<br />        WHEN status BETWEEN 100 AND 199 THEN 'Informational'<br />        WHEN status BETWEEN 200 AND 299 THEN 'Success'<br />        WHEN status BETWEEN 300 AND 399 THEN 'Redirection'<br />        WHEN status BETWEEN 400 AND 499 THEN 'Client Error'<br />        WHEN status BETWEEN 500 AND 599 THEN 'Server Error'<br />        ELSE 'Unknown Status'<br />    END AS status_category,<br />    CASE method<br />        WHEN 'GET' THEN 'Read Operation'<br />        WHEN 'POST' THEN 'Create Operation'<br />        WHEN 'PUT' THEN 'Update Operation'<br />        WHEN 'PATCH' THEN 'Partial Update Operation'<br />        WHEN 'DELETE' THEN 'Delete Operation'<br />        ELSE 'Other Operation'<br />    END AS operation_type,<br />    bytes,<br />    datetime<br />FROM <tableName/logGroup>                         </pre>  | 
| [公用表表达式](#supported-sql-cte) | 在 SELECT、INSERT、UPDATE、DELETE 或 MERGE 语句中创建命名的临时结果集。 | 不支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/negative_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>WITH RequestStats AS (<br />    SELECT <br />        method,<br />        status,<br />        bytes,<br />        COUNT(*) AS request_count<br />    FROM <br />        tableName<br />    GROUP BY <br />        method,<br />        status,<br />        bytes<br />)<br />SELECT <br />    method,<br />    status,<br />    bytes,<br />    request_count <br />FROM <br />    RequestStats <br />WHERE <br />    bytes > 1000</pre>  | 
| [EXPLAIN](#supported-sql-explain) | 显示 SQL 语句的执行计划，但不实际执行该语句。 | 不支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/negative_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>EXPLAIN<br />SELECT <br />    k,<br />    SUM(v)<br />FROM <br />    VALUES <br />        (1, 2),<br />        (1, 3) AS t(k, v)<br />GROUP BY <br />    k</pre>  | 
| [LATERAL SUBQUERY 子句](#supported-sql-lateral-subquery) | 允许 FROM 子句的子查询引用同一 FROM 子句中先前项的列。 | 不支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/negative_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> SELECT <br />    * <br />FROM <br />    tableName<br />LATERAL (<br />    SELECT <br />        * <br />    FROM <br />        t2 <br />    WHERE <br />        t1.c1 = t2.c1<br />)</pre>  | 
| [LATERAL VIEW 子句](#supported-sql-lateral-view) | 通过对基表的每一行应用表生成函数而生成虚拟表。 | 不支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/negative_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    * <br />FROM <br />    tableName<br />LATERAL VIEW <br />    EXPLODE(ARRAY(30, 60)) tableName AS c_age<br />LATERAL VIEW <br />    EXPLODE(ARRAY(40, 80)) AS d_age</pre>  | 
| [LIKE 谓词](#supported-sql-like-predicate) | 使用通配符，将字符串与模式进行匹配。 | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> SELECT <br />    method,<br />    status,<br />    request,<br />    host <br />FROM <br />    <tableName/logGroup> <br />WHERE <br />    method LIKE 'D%'</pre>  | 
| [OFFSET](#supported-sql-offset) | 指定在开始返回查询结果行之前要跳过的行数。 | 在查询中与 LIMIT 子句结合使用时支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg)。例如：[\[See the AWS documentation website for more details\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/supported-directquery-sql.html) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> SELECT <br />    method,<br />    status,<br />    bytes,<br />    datetime <br />FROM <br />    <tableName/logGroup> <br />ORDER BY <br />    datetime<br />OFFSET <br />    10 </pre>  | 
| [PIVOT 子句](#supported-sql-pivot) | 将行转换为列，将数据从基于行的格式转换为基于列的格式。 | 不支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/negative_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    * <br />FROM <br />    (<br />        SELECT <br />            method,<br />            status,<br />            bytes<br />        FROM <br />            <tableName/logGroup><br />    ) AS SourceTable <br />PIVOT <br />(<br />    SUM(bytes) <br />    FOR method IN ('GET', 'POST', 'PATCH', 'PUT', 'DELETE')<br />) AS PivotTable</pre>  | 
| [集合运算符](#supported-sql-set) | 合并两个或多个 SELECT 语句（例如 UNION、INTERSECT、EXCEPT）的结果。 | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    method,<br />    status,<br />    bytes<br />FROM <br />    <tableName/logGroup><br />WHERE <br />    status = '416'<br /><br />UNION<br /><br />SELECT <br />    method,<br />    status,<br />    bytes<br />FROM <br />    <tableName/logGroup><br />WHERE <br />    bytes > 20000</pre>  | 
| [SORT BY 子句](#supported-sql-sort-by) | 指定返回查询结果的顺序。 | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    method,<br />    status,<br />    bytes<br />FROM <br />    <tableName/logGroup><br />SORT BY <br />    bytes DESC</pre>  | 
| [UNPIVOT](#supported-sql-unpivot) | 将列转换为行，将数据从基于列的格式转换为基于行的格式。 | 不支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/negative_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> SELECT <br />    status,<br />    REPLACE(method, '_bytes', '') AS request_method,<br />    bytes,<br />    datetime <br />FROM <br />    PivotedData <br />UNPIVOT <br />(<br />    bytes <br />    FOR method IN <br />    (<br />        GET_bytes,<br />        POST_bytes,<br />        PATCH_bytes,<br />        PUT_bytes,<br />        DELETE_bytes<br />    )<br />) AS UnpivotedData</pre>  | 

## 函数
<a name="supported-sql-functions"></a>

**注意**  
在示例命令列中，根据需要替换 `<tableName/logGroup>`，具体取决于您要查询的数据来源。  
命令示例：`SELECT Body , Operation FROM <tableName/logGroup>`
如果要查询 Amazon S3 或 Security Lake，则使用：`SELECT Body , Operation FROM table_name`
如果您要查询 CloudWatch 日志，请使用：`SELECT Body , Operation FROM `LogGroupA``


| 可用的 SQL 语法 | 说明 | CloudWatch 日志 | Amazon S3 | 安全湖 |  命令示例 | 
| --- | --- | --- | --- | --- | --- | 
| [字符串函数](#supported-sql-string) |  内置函数，可在 SQL 查询中操作和转换字符串及文本数据。例如，转换大小写、合并字符串、提取部分内容以及清理文本。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    UPPER(method) AS upper_method,<br />    LOWER(host) AS lower_host <br />FROM <br />    <tableName/logGroup></pre>  | 
| [日期和时间函数](#supported-sql-date-time) |  内置函数，用于处理和转换查询中的日期和时间戳数据。例如，**date\$1add**、**date\$1format**、**datediff** 和 **current\$1date**。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    TO_TIMESTAMP(datetime) AS timestamp,<br />    TIMESTAMP_SECONDS(UNIX_TIMESTAMP(datetime)) AS from_seconds,<br />    UNIX_TIMESTAMP(datetime) AS to_unix,<br />    FROM_UTC_TIMESTAMP(datetime, 'PST') AS to_pst,<br />    TO_UTC_TIMESTAMP(datetime, 'EST') AS from_est <br />FROM <br />    <tableName/logGroup></pre>  | 
| [聚合函数](#supported-sql-aggregate) |  内置函数，可对多行数据执行计算以生成单个汇总值。例如，**sum**、**count**、**avg**、**max** 和 **min**。  | ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg)支持的 |  支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg)  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    COUNT(*) AS total_records,<br />    COUNT(DISTINCT method) AS unique_methods,<br />    SUM(bytes) AS total_bytes,<br />    AVG(bytes) AS avg_bytes,<br />    MIN(bytes) AS min_bytes,<br />    MAX(bytes) AS max_bytes <br />FROM <br />    <tableName/logGroup></pre>  | 
| [条件函数](#supported-sql-conditional) |  内置函数，根据指定条件执行操作，或在特定条件下评估表达式。例如，**CASE** 和 **IF**。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    CASE <br />        WHEN method = 'GET' AND bytes < 1000 THEN 'Small Read'<br />        WHEN method = 'POST' AND bytes > 10000 THEN 'Large Write'<br />        WHEN status >= 400 OR bytes = 0 THEN 'Problem'<br />        ELSE 'Normal'<br />    END AS request_type <br />FROM <br />    <tableName/logGroup></pre>  | 
| [JSON 函数](#supported-sql-json) |  内置函数，用于在 SQL 查询中解析、提取、修改和查询 JSON 格式的数据（例如，from\$1json、to\$1json、get\$1json\$1object、json\$1tuple），支持对数据集中的 JSON 结构进行操作。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    FROM_JSON(<br />        @message, <br />        'STRUCT<<br />            host: STRING,<br />            user-identifier: STRING,<br />            datetime: STRING,<br />            method: STRING,<br />            status: INT,<br />            bytes: INT<br />        >'<br />    ) AS parsed_json <br />FROM <br />    <tableName/logGroup> </pre>  | 
| [数组函数](#supported-sql-array) |  内置函数，用于在 SQL 查询中处理数组类型列，允许访问、修改和分析数组数据（例如，size、explode、array\$1contains）等操作。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    scores,<br />    size(scores) AS length,<br />    array_contains(scores, 90) AS has_90 <br />FROM <br />    <tableName/logGroup></pre>  | 
| [窗口函数](#supported-sql-window) | 内置函数，可在当前行（窗口）相关的指定行集上执行计算，支持排名、运行总数和移动平均值（例如 ROW\$1NUMBER、RANK、LAG、LEAD）等操作 | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> SELECT <br />    field1,<br />    field2,<br />    RANK() OVER (ORDER BY field2 DESC) AS field2Rank <br />FROM <br />    <tableName/logGroup></pre>  | 
| [转换函数](#supported-sql-conversion) |  内置函数，在 SQL 查询中用于将数据从一种类型转换为另一种类型，支持数据类型转换和格式转换（例如，CAST、TO\$1DATE、TO\$1TIMESTAMP、BINARY）  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    CAST('123' AS INT) AS converted_number,<br />    CAST(123 AS STRING) AS converted_string <br />FROM <br />    <tableName/logGroup></pre>  | 
| [谓词函数](#supported-sql-predicate) |  内置函数，用于评估条件，并根据指定的标准或模式（例如，IN、LIKE、BETWEEN、IS NULL、EXISTS）返回布尔值（true/false）  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    * <br />FROM <br />    <tableName/logGroup> <br />WHERE <br />    id BETWEEN 50000 AND 75000</pre>  | 
| [映射函数](#supported-sql-map) | 对集合中的每个元素应用指定函数，将数据转换为一组新值。 | 不支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/negative_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    MAP_FILTER(<br />        MAP(<br />            'method', method,<br />            'status', CAST(status AS STRING),<br />            'bytes', CAST(bytes AS STRING)<br />        ),<br />        (k, v) -> k IN ('method', 'status') AND v != 'null'<br />    ) AS filtered_map <br />FROM <br />    <tableName/logGroup> <br />WHERE <br />    status = 100</pre>  | 
| [数学函数](#supported-sql-math) | 对数值数据执行数学运算，例如计算平均值、总和或三角函数值。 | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    bytes,<br />    bytes + 1000 AS added,<br />    bytes - 1000 AS subtracted,<br />    bytes * 2 AS doubled,<br />    bytes / 1024 AS kilobytes,<br />    bytes % 1000 AS remainder <br />FROM <br />    <tableName/logGroup></pre>  | 
| [多日志组函数](#multi-log-queries) |  允许用户在 SQL SELECT 语句中指定多个日志组  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 不适用 | 不适用 |  <pre>SELECT <br />    lg1.Column1,<br />    lg1.Column2 <br />FROM <br />    `logGroups(logGroupIdentifier: ['LogGroup1', 'LogGroup2'])` AS lg1 <br />WHERE <br />    lg1.Column3 = "Success"<br /></pre>  | 
| [生成器函数](#supported-sql-generator) | 创建生成值序列的迭代器对象，从而在大型数据集中实现高效的内存使用。 | 不支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/negative_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>SELECT <br />    explode(array(10, 20)) </pre>  | 

## 通用 SQL 限制
<a name="general-sql-restrictions"></a>

将 OpenSearch SQL 与 CloudWatch 日志、Amazon S3 和安全湖一起使用时，必须遵守以下限制。

1. SELECT 语句中仅可使用一个 JOIN 操作。

1. 仅支持一层嵌套子查询。

1. 不支持用分号分隔的多语句查询。

1. 不支持包含相同但仅在大小写上不同的字段名称的查询（例如 field1 和 FIELD1）。

   例如，不支持以下查询：

   ```
   Select AWSAccountId, awsaccountid from LogGroup
   ```

   然而，由于两个日志组中的字段名（@logStream）完全相同，因此可用以下查询：

   ```
   Select a.`@logStream`, b.`@logStream` from Table A INNER Join Table B on a.id = b.id 
   ```

1. 函数和表达式必须对字段名进行操作，并作为包含在 FROM 子句中指定日志组的 SELECT 语句的一部分。

   例如，不支持此查询：

   ```
   SELECT cos(10) FROM LogGroup
   ```

   支持此查询：

   ```
   SELECT cos(field1) FROM LogGroup
   ```

## 为使用 OpenSearch SQL 的 “ CloudWatch 日志见解” 用户提供的更多信息
<a name="supported-sql-for-multi-log-queries"></a>

 CloudWatch 日志支持 OpenSearch Logs Insights 控制台、API 和 CLI 中的 SQL 查询。CloudWatch Logs 支持大多数命令，包括 SELECT、FROM、WHERE、GROUP BY、HAVING、JOINS 和嵌套查询，以及 JSON、数学、字符串和条件函数。但是，L CloudWatch ogs 仅支持读取操作，因此不允许 DDL 或 DML 语句。有关受支持命令和函数的完整列表，请参阅前文各节中的表。

### 多日志组函数
<a name="multi-log-queries"></a>

CloudWatch Logs Insights 支持查询多个日志组的功能。要在 SQL 中处理此使用案例，可使用 `logGroups` 命令。此命令专门用于查询 L CloudWatch ogs Insights 中涉及一个或多个日志组的数据。使用此语法通过在命令中指定多个日志组以进行查询，而不是为每个日志组编写查询并使用 `UNION` 命令以将其进行组合。

语法：

```
`logGroups(
    logGroupIdentifier: ['LogGroup1','LogGroup2', ...'LogGroupn']
)
```

在此语法中，您可在 `logGroupIndentifier` 参数中指定最多 50 个日志组。要引用监控账户中的日志组，请使用 ARNs 而不是`LogGroup`名称。

示例查询：

```
SELECT LG1.Column1, LG1.Column2 from `logGroups(
    logGroupIdentifier: ['LogGroup1', 'LogGroup2']
)` as LG1 
WHERE LG1.Column1 = 'ABC'
```

查询日志时，不支持在语`FROM`句后使用涉及多个 CloudWatch 日志组的以下语法：

```
SELECT Column1, Column2 FROM 'LogGroup1', 'LogGroup2', ...'LogGroupn' 
WHERE Column1 = 'ABC'
```

### 限制
<a name="restrictions"></a>

使用 SQL 或 PPL 命令时，需将特定字段用反引号括起来才能进行查询。包含特殊字符（非字母和非数字）的字段需使用反引号。例如，对 `@message`、`Operation.Export,` 和 `Test::Field` 使用反引号。纯字母名称的列无需使用反引号。

包含简单字段的查询示例：

```
SELECT SessionToken, Operation, StartTime  FROM `LogGroup-A`
LIMIT 1000;
```

附加反引号的相同查询：

```
SELECT `SessionToken`, `Operation`, `StartTime`  FROM `LogGroup-A`
LIMIT 1000;
```

有关不特定于 CloudWatch 日志的其他一般限制，请参阅[通用 SQL 限制](#general-sql-restrictions)。

### 示例查询和限额
<a name="samples"></a>

**注意**  
以下内容适用于 CloudWatch Logs Insights OpenSearch 用户和查询 CloudWatch 数据的用户。

有关可在 CloudWatch 日志中使用的示例 SQL 查询，请参阅 Amazon CloudWatch Logs Insights 控制台中**保存的查询和示例查询**以获取示例。

有关查询 OpenSearch 服务 CloudWatch 日志时适用的限制的信息，请参阅 Amazon Logs 用户指南中的[CloudWatch CloudWatch 日志配额](https://docs.aws.amazon.com/AmazonCloudWatch/latest/logs/cloudwatch_limits_cwl.html)。限制包括您可以查询的 CloudWatch 日志组数量、可以执行的最大并发查询数、最长查询执行时间以及结果中返回的最大行数。无论您使用哪种语言查询 CloudWatch 日志（即 OpenSearch PPL、SQL 和 Logs Insights），限制都是一样的。

### SQL 命令
<a name="supported-sql-commands-details"></a>

**Topics**
+ [

#### 字符串函数
](#supported-sql-string)
+ [

#### 日期和时间函数
](#supported-sql-date-time)
+ [

#### 聚合函数
](#supported-sql-aggregate)
+ [

#### 条件函数
](#supported-sql-conditional)
+ [

#### JSON 函数
](#supported-sql-json)
+ [

#### 数组函数
](#supported-sql-array)
+ [

#### 窗口函数
](#supported-sql-window)
+ [

#### 转换函数
](#supported-sql-conversion)
+ [

#### 谓词函数
](#supported-sql-predicate)
+ [

#### 映射函数
](#supported-sql-map)
+ [

#### 数学函数
](#supported-sql-math)
+ [

#### 生成器函数
](#supported-sql-generator)
+ [

#### SELECT 子句
](#supported-sql-select)
+ [

#### WHERE 子句
](#supported-sql-where)
+ [

#### GROUP BY 子句
](#supported-sql-group-by)
+ [

#### HAVING 子句
](#supported-sql-having)
+ [

#### ORDER BY 子句
](#supported-sql-order-by)
+ [

#### JOIN 子句
](#supported-sql-join)
+ [

#### LIMIT 子句
](#supported-sql-limit)
+ [

#### CASE 子句
](#supported-sql-case)
+ [

#### 公用表表达式
](#supported-sql-cte)
+ [

#### EXPLAIN
](#supported-sql-explain)
+ [

#### LATERAL SUBQUERY 子句
](#supported-sql-lateral-subquery)
+ [

#### LATERAL VIEW 子句
](#supported-sql-lateral-view)
+ [

#### LIKE 谓词
](#supported-sql-like-predicate)
+ [

#### OFFSET
](#supported-sql-offset)
+ [

#### PIVOT 子句
](#supported-sql-pivot)
+ [

#### 集合运算符
](#supported-sql-set)
+ [

#### SORT BY 子句
](#supported-sql-sort-by)
+ [

#### UNPIVOT
](#supported-sql-unpivot)

#### 字符串函数
<a name="supported-sql-string"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。


****  

| 函数 | 说明 | 
| --- | --- | 
| ascii(str) | 返回 str 的第一个字符的数值。 | 
| base64(bin) | 将参数从二进制 bin 转换为 base 64 字符串。 | 
| bit\$1length(expr) | 返回字符串数据的位长度或二进制数据的位数。 | 
| btrim(str) | 删除 str 中首空格字符和尾随空格字符。 | 
| btrim(str, trimStr) | 删除 str 中开头和结尾的 trimStr 字符。 | 
| char(expr) | 返回二进制值等同于 expr 的 ASCII 字符。如果 n 大于 256，则结果等同于 chr(n % 256) | 
| char\$1length(expr) | 返回字符串数据的字符长度或二进制数据的字节数。字符串数据的长度包含尾随空格。二进制数据的长度包含二进制零。 | 
| character\$1length(expr) | 返回字符串数据的字符长度或二进制数据的字节数。字符串数据的长度包含尾随空格。二进制数据的长度包含二进制零。 | 
| chr(expr) | 返回二进制值等同于 expr 的 ASCII 字符。如果 n 大于 256，则结果等同于 chr(n % 256) | 
| concat\$1ws(sep[, str \$1 array(str)]\$1) | 返回以 sep 分隔的字符串连接，跳过 null 值。 | 
| contains(left, right) | 返回一个布尔值。如果在左值中找到右值，则该值为 True。如果任一输入表达式为 NULL，则返回 NULL。否则返回 False。左右两侧都必须是字符串（STRING）或二进制（BINARY）类型。 | 
| decode(bin, charset) | 使用第二个参数字符集解码第一个参数。 | 
| decode(expr, search, result [, search, result ] ... [, default]) | 按顺序将 expr 与每个搜索值进行比较。如果 expr 等于搜索值，解码函数将返回对应的结果。如果未找到匹配项，则返回默认值。如果省略默认值，则返回 null。 | 
| elt(n, input1, input2, ...) | 返回第 n 个输入，例如，当n 为 2 时返回 input2。 | 
| encode(str, charset) | 使用第二个参数字符集编码第一个参数。 | 
| endswith(left, right) | 返回一个布尔值。如果左值以右值结尾，则该值为 True。如果任一输入表达式为 NULL，则返回 NULL。否则返回 False。左右两侧都必须是字符串（STRING）或二进制（BINARY）类型。 | 
| find\$1in\$1set(str, str\$1array) | 返回给定字符串（str）在逗号分隔列表（str\$1array）中的索引（从 1 开始计数）。如果未找到字符串或给定字符串（str）包含逗号，则返回 0。 | 
| format\$1number(expr1, expr2) | 将数字 expr1 格式化为“\$1,\$1\$1\$1,\$1\$1\$1.\$1\$1”，并四舍五入至 expr2 小数位。如果 expr2 为 0，则结果不包含小数点或分数部分。expr2 也接受用户指定的格式。这与 MySQL 的 FORMAT 函数类似。 | 
| format\$1string(strfmt, obj, ...) | 根据 printf 样式的格式字符串返回格式化字符串。 | 
| initcap(str) | 返回 str，其中每个单词的首字母大写。所有其他字母均为小写。单词由空格进行分隔。 | 
| instr(str, substr) | 返回 str 中 substr 首次出现的索引（从 1 开始计数）。 | 
| lcase(str) | 返回 str，其中所有字符均转换为小写。 | 
| left(str, len) | 返回字符串 str 中最左侧（len可以是字符串类型）的 len 个字符，如果 len 小于或等于 0，则结果为空字符串。 | 
| len(expr) | 返回字符串数据的字符长度或二进制数据的字节数。字符串数据的长度包含尾随空格。二进制数据的长度包含二进制零。 | 
| length(expr) | 返回字符串数据的字符长度或二进制数据的字节数。字符串数据的长度包含尾随空格。二进制数据的长度包含二进制零。 | 
| levenshtein(str1, str2[, threshold]) | 返回两个给定字符串之间的 Levenshtein 距离。如果已设置阈值且距离大于该阈值，则返回 -1。 | 
| locate(substr, str[, pos]) | 返回在位置 pos 之后，str 中 substr 首次出现的位置。给定 pos 和返回值均从 1 开始计数。 | 
| lower(str) | 返回 str，其中所有字符均转换为小写。 | 
| lpad(str, len[, pad]) | 返回 str，用 pad 向左填充至 len 的长度。如果 str 比 len 长，则返回值将缩短至 len 个字符或字节。如果未指定 pad，则当 str 为字符串时，将在其左侧用空格字符填充；当其为字节序列时，则用零填充。 | 
| ltrim(str) | 删除 str 中首空格字符。 | 
| luhn\$1check(str ) | 根据 Luhn 算法检查数字的字符串是否有效。该校验函数广泛应用于信用卡号和政府身份证号码，用于区分有效号码与输入错误或不正确的号码。 | 
| mask(input[, upperChar, lowerChar, digitChar, otherChar]) | 对给定的字符串值进行掩码处理。该函数将字符替换为“X”或“x”，将数字替换为“n”。这有助于创建去除敏感信息的表格副本。 | 
| octet\$1length(expr) | 返回字符串数据的字节长度或二进制数据的字节数。 | 
| overlay(input, replace, pos[, len]) | 将 input 替换为 replace，开头为 pos 且长度为 len。 | 
| position(substr, str[, pos]) | 返回在位置 pos 之后，str 中 substr 首次出现的位置。给定 pos 和返回值均从 1 开始计数。 | 
| printf(strfmt, obj, ...) | 根据 printf 样式的格式字符串返回格式化字符串。 | 
| regexp\$1count(str, regexp) | 返回正则表达式模式 regexp 在字符串 str 中匹配的次数。 | 
| regexp\$1extract(str, regexp[, idx]) | 提取 str 中与表达式匹配且对应 regexp 正则表达式组索引的第一个字符串。 | 
| regexp\$1extract\$1all(str, regexp[, idx]) | 提取 str 中与表达式匹配且对应 regexp 正则表达式组索引的所有字符串。 | 
| regexp\$1instr(str, regexp) | 在字符串中搜索正则表达式，并返回指示匹配子字符串开始位置的整数。位置从 1 开始计数，而不是从 0 开始计数。如果未找到匹配项，则返回 0。 | 
| regexp\$1replace(str, regexp, rep[, position]) | 将 str 中所有匹配 regexp 的子字符串替换为 rep。 | 
| regexp\$1substr(str, regexp) | 返回字符串 str 中与正则表达式 regexp 匹配的子字符串。如果未找到正则表达式，则结果为 null。 | 
| repeat(str, n) | 返回将给定字符串重复 n 次的字符串。 | 
| replace(str, search[, replace]) | 将所有出现的 search 替换为 replace。 | 
| right(str, len) | 返回字符串 str 中最右侧（len可以是字符串类型）的 len 个字符，如果 len 小于或等于 0，则结果为空字符串。 | 
| rpad(str, len[, pad]) | 返回 str，用 pad 向右填充至 len 的长度。如果 str 比 len 长，则返回值将缩短至 len 个字符。如果未指定 pad，则当 str 为字符串时，将在其右侧用空格字符填充；当其为二进制字符串时，则用零填充。 | 
| rtrim(str) | 删除 str 中结尾的空格字符。 | 
| sentences(str[, lang, country]) | 将 str 拆分成由单词组成的数组。 | 
| soundex(str) | 返回字符串的 Soundex 代码。 | 
| space(n) | 返回由 n 个空格组成的字符串。 | 
| split(str, regex, limit) | 将 str 按匹配 regex 的出现次数进行拆分，并返回一个长度不超过 limit 的数组 | 
| split\$1part(str, delimiter, partNum) | 将 str 按分隔符进行拆分，并返回请求的拆分部分（从 1 开始计数）。如果任何输入为 null，则返回 null。如果 partNum 超出拆分部分的范围，则返回空字符串。如果 partNum 为 0，则引发错误。如果 partNum 为负数，则从字符串末尾开始倒序计数。如果 delimiter 为空字符串，则未拆分 str。 | 
| startswith(left, right) | 返回一个布尔值。如果左值以右值开始，则该值为 True。如果任一输入表达式为 NULL，则返回 NULL。否则返回 False。左右两侧都必须是字符串（STRING）或二进制（BINARY）类型。 | 
| substr(str, pos[, len]) | 返回 len 的子字符串，其开头为 pos 且长度为 str 的，或者返回字节数组的片段，其开头为 pos 且长度为 len。 | 
| substr(str FROM pos[ FOR len]]) | 返回 len 的子字符串，其开头为 pos 且长度为 str 的，或者返回字节数组的片段，其开头为 pos 且长度为 len。 | 
| substring(str, pos[, len]) | 返回 len 的子字符串，其开头为 pos 且长度为 str 的，或者返回字节数组的片段，其开头为 pos 且长度为 len。 | 
| substring(str FROM pos[ FOR len]]) | 返回 len 的子字符串，其开头为 pos 且长度为 str 的，或者返回字节数组的片段，其开头为 pos 且长度为 len。 | 
| substring\$1index(str, delim, count) | 从 str 返回分隔符 delim 出现 count 次之前的子字符串。如果 count 为正，则返回最终分隔符左侧的所有内容（从左侧开始计数）。如果 count 为负，则返回最终分隔符右侧的所有内容（从右侧开始计数）。函数 substring\$1index 在搜索 delim 时执行区分大小写的匹配。 | 
| to\$1binary(str[, fmt]) | 根据提供的 fmt，将输入 str 转换为二进制值。fmt 可以是不区分大小写的字符串常量，取值为“hex”、“utf-8”、“utf8”或“base64”。默认情况下，如果 fmt 省略，则转换的二进制格式为“hex”。如果至少一个输入参数为 NULL，则该函数返回 NULL。 | 
| to\$1char(numberExpr, formatExpr) | 基于 formatExpr，将 numberExpr 转换为字符串。如果转换失败，则引发异常。格式可包含以下字符（不区分大小写）：“0”或“9”：表示预期为 0 到 9 之间的数字。格式字符串中 0 或 9 序列匹配输入值中的数字序列，生成与格式字符串中对应序列长度相同的输出字符串。如果 0/9 序列的位数多于十进制值的匹配部分，且以 0 开头并位于小数点前，则结果字符串将用零填充左侧。否则，则用空格填充。“.”或“D”：指定小数点的位置（可选，仅允许出现一次）。“,”或“G”：指定千位分隔符（,）的位置。每组分隔符的左右两侧必须分别有数字 0 或 9。 | 
| to\$1number(expr, fmt) | 将字符串“expr”转换为基于字符串格式“fmt”的数字。如果转换失败，则引发异常。格式可包含以下字符（不区分大小写）：“0”或“9”：表示预期为 0 到 9 之间的数字。格式字符串中的 0 或 9 序列匹配输入字符串中的数字序列。如果 0/9 序列以 0 开头且位于小数点前，则只能匹配相同长度的数字序列。否则，如果序列以 9 开头或位于小数点后，则可匹配大小相同或更小的数字序列。“.”或“D”：指定小数点的位置（可选，仅允许出现一次）。“,”或“G”：指定千位分隔符（,）的位置。每组分隔符的左右两侧必须分别有数字 0 或 9。“expr”必须与数字大小相关的分组分隔符相匹配。 | 
| to\$1varchar(numberExpr, formatExpr) | 基于 formatExpr，将 numberExpr 转换为字符串。如果转换失败，则引发异常。格式可包含以下字符（不区分大小写）：“0”或“9”：表示预期为 0 到 9 之间的数字。格式字符串中 0 或 9 序列匹配输入值中的数字序列，生成与格式字符串中对应序列长度相同的输出字符串。如果 0/9 序列的位数多于十进制值的匹配部分，且以 0 开头并位于小数点前，则结果字符串将用零填充左侧。否则，则用空格填充。“.”或“D”：指定小数点的位置（可选，仅允许出现一次）。“,”或“G”：指定千位分隔符（,）的位置。每组分隔符的左右两侧必须分别有数字 0 或 9。 | 
| translate(input, from, to) | 转换 input 字符串，方法是将 from 字符串中出现的字符替换为 to 字符串中的相应字符。 | 
| trim(str) | 删除 str 中首空格字符和尾随空格字符。 | 
| trim(BOTH FROM str) | 删除 str 中首空格字符和尾随空格字符。 | 
| trim(LEADING FROM str) | 删除 str 中首空格字符。 | 
| trim(TRAILING FROM str) | 删除 str 中结尾的空格字符。 | 
| trim(trimStr FROM str) | 删除 str 中开头和结尾的 trimStr 字符。 | 
| trim(BOTH trimStr FROM str) | 删除 str 中开头和结尾的 trimStr 字符。 | 
| trim(LEADING trimStr FROM str) | 删除 str 中开头的 trimStr 字符。 | 
| trim(TRAILING trimStr FROM str) | 删除 str 中结尾的 trimStr 字符。 | 
| try\$1to\$1binary(str[, fmt]) | 这是 to\$1binary 的特殊版本，执行相同操作，但在转换无法完成时返回 NULL 值而非引发错误。 | 
| try\$1to\$1number(expr, fmt) | 将字符串“expr”转换为基于字符串格式 fmt 的数字。如果字符串“expr”与预期格式不匹配，则返回 NULL。该格式遵循与 to\$1number 函数相同的语义。 | 
| ucase(str) | 返回 str，其中所有字符均转换为大写。 | 
| unbase64(str) | 将参数从 base 64 字符串 str 转换为二进制。 | 
| upper(str) | 返回 str，其中所有字符均转换为大写。 | 



**示例**

```
-- ascii
SELECT ascii('222');
+----------+
|ascii(222)|
+----------+
|        50|
+----------+
SELECT ascii(2);
+--------+
|ascii(2)|
+--------+
|      50|
+--------+
-- base64
SELECT base64('Feathers');
+-----------------+
|base64(Feathers)|
+-----------------+
|     RmVhdGhlcnM=|
+-----------------+
SELECT base64(x'537061726b2053514c');
+-----------------------------+
|base64(X'537061726B2053514C')|
+-----------------------------+
|                 U3BhcmsgU1FM|
+-----------------------------+
-- bit_length
SELECT bit_length('Feathers');
+---------------------+
|bit_length(Feathers)|
+---------------------+
|                   64|
+---------------------+
SELECT bit_length(x'537061726b2053514c');
+---------------------------------+
|bit_length(X'537061726B2053514C')|
+---------------------------------+
|                               72|
+---------------------------------+
-- btrim
SELECT btrim('    Feathers   ');
+----------------------+
|btrim(    Feathers   )|
+----------------------+
|              Feathers|
+----------------------+
SELECT btrim(encode('    Feathers   ', 'utf-8'));
+-------------------------------------+
|btrim(encode(    Feathers   , utf-8))|
+-------------------------------------+
|                             Feathers|
+-------------------------------------+
SELECT btrim('Feathers', 'Fe');
+---------------------+
|btrim(Alphabet, Al)|
+---------------------+
|               athers|
+---------------------+
SELECT btrim(encode('Feathers', 'utf-8'), encode('Al', 'utf-8'));
+---------------------------------------------------+
|btrim(encode(Feathers, utf-8), encode(Al, utf-8))|
+---------------------------------------------------+
|                                             athers|
+---------------------------------------------------+
-- char
SELECT char(65);
+--------+
|char(65)|
+--------+
|       A|
+--------+
-- char_length
SELECT char_length('Feathers ');
+-----------------------+
|char_length(Feathers )|
+-----------------------+
|                     9 |
+-----------------------+
SELECT char_length(x'537061726b2053514c');
+----------------------------------+
|char_length(X'537061726B2053514C')|
+----------------------------------+
|                                 9|
+----------------------------------+
SELECT CHAR_LENGTH('Feathers ');
+-----------------------+
|char_length(Feathers )|
+-----------------------+
|                     9|
+-----------------------+
SELECT CHARACTER_LENGTH('Feathers ');
+----------------------------+
|character_length(Feathers )|
+----------------------------+
|                          9|
+----------------------------+
-- character_length
SELECT character_length('Feathers ');
+----------------------------+
|character_length(Feathers )|
+----------------------------+
|                          9|
+----------------------------+
SELECT character_length(x'537061726b2053514c');
+---------------------------------------+
|character_length(X'537061726B2053514C')|
+---------------------------------------+
|                                      9|
+---------------------------------------+
SELECT CHAR_LENGTH('Feathers ');
+-----------------------+
|char_length(Feathers )|
+-----------------------+
|                     9|
+-----------------------+
SELECT CHARACTER_LENGTH('Feathers ');
+----------------------------+
|character_length(Feathers )|
+----------------------------+
|                          9|
+----------------------------+
-- chr
SELECT chr(65);
+-------+
|chr(65)|
+-------+
|      A|
+-------+
-- concat_ws
SELECT concat_ws(' ', 'Fea', 'thers');
+------------------------+
|concat_ws( , Fea, thers)|
+------------------------+
|               Feathers|
+------------------------+
SELECT concat_ws('s');
+------------+
|concat_ws(s)|
+------------+
|            |
+------------+
SELECT concat_ws('/', 'foo', null, 'bar');
+----------------------------+
|concat_ws(/, foo, NULL, bar)|
+----------------------------+
|                     foo/bar|
+----------------------------+
SELECT concat_ws(null, 'Fea', 'thers');
+---------------------------+
|concat_ws(NULL, Fea, thers)|
+---------------------------+
|                       NULL|
+---------------------------+
-- contains
SELECT contains('Feathers', 'Fea');
+--------------------------+
|contains(Feathers, Fea)|
+--------------------------+
|                      true|
+--------------------------+
SELECT contains('Feathers', 'SQL');
+--------------------------+
|contains(Feathers, SQL)|
+--------------------------+
|                     false|
+--------------------------+
SELECT contains('Feathers', null);
+-------------------------+
|contains(Feathers, NULL)|
+-------------------------+
|                     NULL|
+-------------------------+
SELECT contains(x'537061726b2053514c', x'537061726b');
+----------------------------------------------+
|contains(X'537061726B2053514C', X'537061726B')|
+----------------------------------------------+
|                                          true|
+----------------------------------------------+
-- decode
SELECT decode(encode('abc', 'utf-8'), 'utf-8');
+---------------------------------+
|decode(encode(abc, utf-8), utf-8)|
+---------------------------------+
|                              abc|
+---------------------------------+
SELECT decode(2, 1, 'Southlake', 2, 'San Francisco', 3, 'New Jersey', 4, 'Seattle', 'Non domestic');
+----------------------------------------------------------------------------------+
|decode(2, 1, Southlake, 2, San Francisco, 3, New Jersey, 4, Seattle, Non domestic)|
+----------------------------------------------------------------------------------+
|                                                                     San Francisco|
+----------------------------------------------------------------------------------+
SELECT decode(6, 1, 'Southlake', 2, 'San Francisco', 3, 'New Jersey', 4, 'Seattle', 'Non domestic');
+----------------------------------------------------------------------------------+
|decode(6, 1, Southlake, 2, San Francisco, 3, New Jersey, 4, Seattle, Non domestic)|
+----------------------------------------------------------------------------------+
|                                                                      Non domestic|
+----------------------------------------------------------------------------------+
SELECT decode(6, 1, 'Southlake', 2, 'San Francisco', 3, 'New Jersey', 4, 'Seattle');
+--------------------------------------------------------------------+
|decode(6, 1, Southlake, 2, San Francisco, 3, New Jersey, 4, Seattle)|
+--------------------------------------------------------------------+
|                                                                NULL|
+--------------------------------------------------------------------+
SELECT decode(null, 6, 'Fea', NULL, 'thers', 4, 'rock');
+-------------------------------------------+
|decode(NULL, 6, Fea, NULL, thers, 4, rock)|
+-------------------------------------------+
|                                      thers|
+-------------------------------------------+
-- elt
SELECT elt(1, 'scala', 'java');
+-------------------+
|elt(1, scala, java)|
+-------------------+
|              scala|
+-------------------+
SELECT elt(2, 'a', 1);
+------------+
|elt(2, a, 1)|
+------------+
|           1|
+------------+
-- encode
SELECT encode('abc', 'utf-8');
+------------------+
|encode(abc, utf-8)|
+------------------+
|        [61 62 63]|
+------------------+
-- endswith
SELECT endswith('Feathers', 'ers');
+------------------------+
|endswith(Feathers, ers)|
+------------------------+
|                    true|
+------------------------+
SELECT endswith('Feathers', 'SQL');
+--------------------------+
|endswith(Feathers, SQL)|
+--------------------------+
|                     false|
+--------------------------+
SELECT endswith('Feathers', null);
+-------------------------+
|endswith(Feathers, NULL)|
+-------------------------+
|                     NULL|
+-------------------------+
SELECT endswith(x'537061726b2053514c', x'537061726b');
+----------------------------------------------+
|endswith(X'537061726B2053514C', X'537061726B')|
+----------------------------------------------+
|                                         false|
+----------------------------------------------+
SELECT endswith(x'537061726b2053514c', x'53514c');
+------------------------------------------+
|endswith(X'537061726B2053514C', X'53514C')|
+------------------------------------------+
|                                      true|
+------------------------------------------+
-- find_in_set
SELECT find_in_set('ab','abc,b,ab,c,def');
+-------------------------------+
|find_in_set(ab, abc,b,ab,c,def)|
+-------------------------------+
|                              3|
+-------------------------------+
-- format_number
SELECT format_number(12332.123456, 4);
+------------------------------+
|format_number(12332.123456, 4)|
+------------------------------+
|                   12,332.1235|
+------------------------------+
SELECT format_number(12332.123456, '##################.###');
+---------------------------------------------------+
|format_number(12332.123456, ##################.###)|
+---------------------------------------------------+
|                                          12332.123|
+---------------------------------------------------+
-- format_string
SELECT format_string("Hello World %d %s", 100, "days");
+-------------------------------------------+
|format_string(Hello World %d %s, 100, days)|
+-------------------------------------------+
|                       Hello World 100 days|
+-------------------------------------------+
-- initcap
SELECT initcap('Feathers');
+------------------+
|initcap(Feathers)|
+------------------+
|         Feathers|
+------------------+
-- instr
SELECT instr('Feathers', 'ers');
+--------------------+
|instr(Feathers, ers)|
+--------------------+
|                   6|
+--------------------+
-- lcase
SELECT lcase('Feathers');
+---------------+
|lcase(Feathers)|
+---------------+
|       feathers|
+---------------+
-- left
SELECT left('Feathers', 3);
+------------------+
|left(Feathers, 3)|
+------------------+
|               Fea|
+------------------+
SELECT left(encode('Feathers', 'utf-8'), 3);
+---------------------------------+
|left(encode(Feathers, utf-8), 3)|
+---------------------------------+
|                       [RmVh]|
+---------------------------------+
-- len
SELECT len('Feathers ');
+---------------+
|len(Feathers )|
+---------------+
|             9|
+---------------+
SELECT len(x'537061726b2053514c');
+--------------------------+
|len(X'537061726B2053514C')|
+--------------------------+
|                         9|
+--------------------------+
SELECT CHAR_LENGTH('Feathers ');
+-----------------------+
|char_length(Feathers )|
+-----------------------+
|                     9|
+-----------------------+
SELECT CHARACTER_LENGTH('Feathers ');
+----------------------------+
|character_length(Feathers )|
+----------------------------+
|                          9|
+----------------------------+
-- length
SELECT length('Feathers ');
+------------------+
|length(Feathers )|
+------------------+
|                9|
+------------------+
SELECT length(x'537061726b2053514c');
+-----------------------------+
|length(X'537061726B2053514C')|
+-----------------------------+
|                            9|
+-----------------------------+
SELECT CHAR_LENGTH('Feathers ');
+-----------------------+
|char_length(Feathers )|
+-----------------------+
|                     9|
+-----------------------+
SELECT CHARACTER_LENGTH('Feathers ');
+----------------------------+
|character_length(Feathers )|
+----------------------------+
|                          9|
+----------------------------+
-- levenshtein
SELECT levenshtein('kitten', 'sitting');
+----------------------------+
|levenshtein(kitten, sitting)|
+----------------------------+
|                           3|
+----------------------------+
SELECT levenshtein('kitten', 'sitting', 2);
+-------------------------------+
|levenshtein(kitten, sitting, 2)|
+-------------------------------+
|                             -1|
+-------------------------------+
-- locate
SELECT locate('bar', 'foobarbar');
+-------------------------+
|locate(bar, foobarbar, 1)|
+-------------------------+
|                        4|
+-------------------------+
SELECT locate('bar', 'foobarbar', 5);
+-------------------------+
|locate(bar, foobarbar, 5)|
+-------------------------+
|                        7|
+-------------------------+
SELECT POSITION('bar' IN 'foobarbar');
+-------------------------+
|locate(bar, foobarbar, 1)|
+-------------------------+
|                        4|
+-------------------------+
-- lower
SELECT lower('Feathers');
+---------------+
|lower(Feathers)|
+---------------+
|       feathers|
+---------------+
-- lpad
SELECT lpad('hi', 5, '??');
+---------------+
|lpad(hi, 5, ??)|
+---------------+
|          ???hi|
+---------------+
SELECT lpad('hi', 1, '??');
+---------------+
|lpad(hi, 1, ??)|
+---------------+
|              h|
+---------------+
SELECT lpad('hi', 5);
+--------------+
|lpad(hi, 5,  )|
+--------------+
|            hi|
+--------------+
SELECT hex(lpad(unhex('aabb'), 5));
+--------------------------------+
|hex(lpad(unhex(aabb), 5, X'00'))|
+--------------------------------+
|                      000000AABB|
+--------------------------------+
SELECT hex(lpad(unhex('aabb'), 5, unhex('1122')));
+--------------------------------------+
|hex(lpad(unhex(aabb), 5, unhex(1122)))|
+--------------------------------------+
|                            112211AABB|
+--------------------------------------+
-- ltrim
SELECT ltrim('    Feathers   ');
+----------------------+
|ltrim(    Feathers   )|
+----------------------+
|           Feathers   |
+----------------------+
-- luhn_check
SELECT luhn_check('8112189876');
+----------------------+
|luhn_check(8112189876)|
+----------------------+
|                  true|
+----------------------+
SELECT luhn_check('79927398713');
+-----------------------+
|luhn_check(79927398713)|
+-----------------------+
|                   true|
+-----------------------+
SELECT luhn_check('79927398714');
+-----------------------+
|luhn_check(79927398714)|
+-----------------------+
|                  false|
+-----------------------+
-- mask
SELECT mask('abcd-EFGH-8765-4321');
+----------------------------------------+
|mask(abcd-EFGH-8765-4321, X, x, n, NULL)|
+----------------------------------------+
|                     xxxx-XXXX-nnnn-nnnn|
+----------------------------------------+
SELECT mask('abcd-EFGH-8765-4321', 'Q');
+----------------------------------------+
|mask(abcd-EFGH-8765-4321, Q, x, n, NULL)|
+----------------------------------------+
|                     xxxx-QQQQ-nnnn-nnnn|
+----------------------------------------+
SELECT mask('AbCD123-@$#', 'Q', 'q');
+--------------------------------+
|mask(AbCD123-@$#, Q, q, n, NULL)|
+--------------------------------+
|                     QqQQnnn-@$#|
+--------------------------------+
SELECT mask('AbCD123-@$#');
+--------------------------------+
|mask(AbCD123-@$#, X, x, n, NULL)|
+--------------------------------+
|                     XxXXnnn-@$#|
+--------------------------------+
SELECT mask('AbCD123-@$#', 'Q');
+--------------------------------+
|mask(AbCD123-@$#, Q, x, n, NULL)|
+--------------------------------+
|                     QxQQnnn-@$#|
+--------------------------------+
SELECT mask('AbCD123-@$#', 'Q', 'q');
+--------------------------------+
|mask(AbCD123-@$#, Q, q, n, NULL)|
+--------------------------------+
|                     QqQQnnn-@$#|
+--------------------------------+
SELECT mask('AbCD123-@$#', 'Q', 'q', 'd');
+--------------------------------+
|mask(AbCD123-@$#, Q, q, d, NULL)|
+--------------------------------+
|                     QqQQddd-@$#|
+--------------------------------+
SELECT mask('AbCD123-@$#', 'Q', 'q', 'd', 'o');
+-----------------------------+
|mask(AbCD123-@$#, Q, q, d, o)|
+-----------------------------+
|                  QqQQdddoooo|
+-----------------------------+
SELECT mask('AbCD123-@$#', NULL, 'q', 'd', 'o');
+--------------------------------+
|mask(AbCD123-@$#, NULL, q, d, o)|
+--------------------------------+
|                     AqCDdddoooo|
+--------------------------------+
SELECT mask('AbCD123-@$#', NULL, NULL, 'd', 'o');
+-----------------------------------+
|mask(AbCD123-@$#, NULL, NULL, d, o)|
+-----------------------------------+
|                        AbCDdddoooo|
+-----------------------------------+
SELECT mask('AbCD123-@$#', NULL, NULL, NULL, 'o');
+--------------------------------------+
|mask(AbCD123-@$#, NULL, NULL, NULL, o)|
+--------------------------------------+
|                           AbCD123oooo|
+--------------------------------------+
SELECT mask(NULL, NULL, NULL, NULL, 'o');
+-------------------------------+
|mask(NULL, NULL, NULL, NULL, o)|
+-------------------------------+
|                           NULL|
+-------------------------------+
SELECT mask(NULL);
+-------------------------+
|mask(NULL, X, x, n, NULL)|
+-------------------------+
|                     NULL|
+-------------------------+
SELECT mask('AbCD123-@$#', NULL, NULL, NULL, NULL);
+-----------------------------------------+
|mask(AbCD123-@$#, NULL, NULL, NULL, NULL)|
+-----------------------------------------+
|                              AbCD123-@$#|
+-----------------------------------------+
-- octet_length
SELECT octet_length('Feathers');
+-----------------------+
|octet_length(Feathers)|
+-----------------------+
|                      8|
+-----------------------+
SELECT octet_length(x'537061726b2053514c');
+-----------------------------------+
|octet_length(X'537061726B2053514C')|
+-----------------------------------+
|                                  9|
+-----------------------------------+
-- overlay
SELECT overlay('Feathers' PLACING '_' FROM 6);
+----------------------------+
|overlay(Feathers, _, 6, -1)|
+----------------------------+
|                   Feathe_ers|
+----------------------------+
SELECT overlay('Feathers' PLACING 'ures' FROM 5);
+-------------------------------+
|overlay(Feathers, ures, 5, -1)|
+-------------------------------+
|                     Features  |
+-------------------------------+
-- position
SELECT position('bar', 'foobarbar');
+---------------------------+
|position(bar, foobarbar, 1)|
+---------------------------+
|                          4|
+---------------------------+
SELECT position('bar', 'foobarbar', 5);
+---------------------------+
|position(bar, foobarbar, 5)|
+---------------------------+
|                          7|
+---------------------------+
SELECT POSITION('bar' IN 'foobarbar');
+-------------------------+
|locate(bar, foobarbar, 1)|
+-------------------------+
|                        4|
+-------------------------+
-- printf
SELECT printf("Hello World %d %s", 100, "days");
+------------------------------------+
|printf(Hello World %d %s, 100, days)|
+------------------------------------+
|                Hello World 100 days|
+------------------------------------+
-- regexp_count
SELECT regexp_count('Steven Jones and Stephen Smith are the best players', 'Ste(v|ph)en');
+------------------------------------------------------------------------------+
|regexp_count(Steven Jones and Stephen Smith are the best players, Ste(v|ph)en)|
+------------------------------------------------------------------------------+
|                                                                             2|
+------------------------------------------------------------------------------+
SELECT regexp_count('abcdefghijklmnopqrstuvwxyz', '[a-z]{3}');
+--------------------------------------------------+
|regexp_count(abcdefghijklmnopqrstuvwxyz, [a-z]{3})|
+--------------------------------------------------+
|                                                 8|
+--------------------------------------------------+
-- regexp_extract
SELECT regexp_extract('100-200', '(\\d+)-(\\d+)', 1);
+---------------------------------------+
|regexp_extract(100-200, (\d+)-(\d+), 1)|
+---------------------------------------+
|                                    100|
+---------------------------------------+
-- regexp_extract_all
SELECT regexp_extract_all('100-200, 300-400', '(\\d+)-(\\d+)', 1);
+----------------------------------------------------+
|regexp_extract_all(100-200, 300-400, (\d+)-(\d+), 1)|
+----------------------------------------------------+
|                                          [100, 300]|
+----------------------------------------------------+
-- regexp_instr
SELECT regexp_instr('user@opensearch.org', '@[^.]*');
+----------------------------------------------+
|regexp_instr(user@opensearch.org, @[^.]*, 0)|
+----------------------------------------------+
|                                             5|
+----------------------------------------------+
-- regexp_replace
SELECT regexp_replace('100-200', '(\\d+)', 'num');
+--------------------------------------+
|regexp_replace(100-200, (\d+), num, 1)|
+--------------------------------------+
|                               num-num|
+--------------------------------------+
-- regexp_substr
SELECT regexp_substr('Steven Jones and Stephen Smith are the best players', 'Ste(v|ph)en');
+-------------------------------------------------------------------------------+
|regexp_substr(Steven Jones and Stephen Smith are the best players, Ste(v|ph)en)|
+-------------------------------------------------------------------------------+
|                                                                         Steven|
+-------------------------------------------------------------------------------+
SELECT regexp_substr('Steven Jones and Stephen Smith are the best players', 'Jeck');
+------------------------------------------------------------------------+
|regexp_substr(Steven Jones and Stephen Smith are the best players, Jeck)|
+------------------------------------------------------------------------+
|                                                                    NULL|
+------------------------------------------------------------------------+
-- repeat
SELECT repeat('123', 2);
+--------------+
|repeat(123, 2)|
+--------------+
|        123123|
+--------------+
-- replace
SELECT replace('ABCabc', 'abc', 'DEF');
+-------------------------+
|replace(ABCabc, abc, DEF)|
+-------------------------+
|                   ABCDEF|
+-------------------------+
-- right
SELECT right('Feathers', 3);
+-------------------+
|right(Feathers, 3)|
+-------------------+
|                ers|
+-------------------+
-- rpad
SELECT rpad('hi', 5, '??');
+---------------+
|rpad(hi, 5, ??)|
+---------------+
|          hi???|
+---------------+
SELECT rpad('hi', 1, '??');
+---------------+
|rpad(hi, 1, ??)|
+---------------+
|              h|
+---------------+
SELECT rpad('hi', 5);
+--------------+
|rpad(hi, 5,  )|
+--------------+
|         hi   |
+--------------+
SELECT hex(rpad(unhex('aabb'), 5));
+--------------------------------+
|hex(rpad(unhex(aabb), 5, X'00'))|
+--------------------------------+
|                      AABB000000|
+--------------------------------+
SELECT hex(rpad(unhex('aabb'), 5, unhex('1122')));
+--------------------------------------+
|hex(rpad(unhex(aabb), 5, unhex(1122)))|
+--------------------------------------+
|                            AABB112211|
+--------------------------------------+
-- rtrim
SELECT rtrim('    Feathers   ');
+----------------------+
|rtrim(    Feathers   )|
+----------------------+
|              Feathers|
+----------------------+
-- sentences
SELECT sentences('Hi there! Good morning.');
+--------------------------------------+
|sentences(Hi there! Good morning., , )|
+--------------------------------------+
|                  [[Hi, there], [Go...|
+--------------------------------------+
-- soundex
SELECT soundex('Miller');
+---------------+
|soundex(Miller)|
+---------------+
|           M460|
+---------------+
-- space
SELECT concat(space(2), '1');
+-------------------+
|concat(space(2), 1)|
+-------------------+
|                  1|
+-------------------+
-- split
SELECT split('oneAtwoBthreeC', '[ABC]');
+--------------------------------+
|split(oneAtwoBthreeC, [ABC], -1)|
+--------------------------------+
|             [one, two, three, ]|
+--------------------------------+
SELECT split('oneAtwoBthreeC', '[ABC]', -1);
+--------------------------------+
|split(oneAtwoBthreeC, [ABC], -1)|
+--------------------------------+
|             [one, two, three, ]|
+--------------------------------+
SELECT split('oneAtwoBthreeC', '[ABC]', 2);
+-------------------------------+
|split(oneAtwoBthreeC, [ABC], 2)|
+-------------------------------+
|              [one, twoBthreeC]|
+-------------------------------+
-- split_part
SELECT split_part('11.12.13', '.', 3);
+--------------------------+
|split_part(11.12.13, ., 3)|
+--------------------------+
|                        13|
+--------------------------+
-- startswith
SELECT startswith('Feathers', 'Fea');
+----------------------------+
|startswith(Feathers, Fea)|
+----------------------------+
|                        true|
+----------------------------+
SELECT startswith('Feathers', 'SQL');
+--------------------------+
|startswith(Feathers, SQL)|
+--------------------------+
|                     false|
+--------------------------+
SELECT startswith('Feathers', null);
+---------------------------+
|startswith(Feathers, NULL)|
+---------------------------+
|                       NULL|
+---------------------------+
SELECT startswith(x'537061726b2053514c', x'537061726b');
+------------------------------------------------+
|startswith(X'537061726B2053514C', X'537061726B')|
+------------------------------------------------+
|                                            true|
+------------------------------------------------+
SELECT startswith(x'537061726b2053514c', x'53514c');
+--------------------------------------------+
|startswith(X'537061726B2053514C', X'53514C')|
+--------------------------------------------+
|                                       false|
+--------------------------------------------+
-- substr
SELECT substr('Feathers', 5);
+--------------------------------+
|substr(Feathers, 5, 2147483647)|
+--------------------------------+
|                           hers |
+--------------------------------+
SELECT substr('Feathers', -3);
+---------------------------------+
|substr(Feathers, -3, 2147483647)|
+---------------------------------+
|                              ers|
+---------------------------------+
SELECT substr('Feathers', 5, 1);
+-----------------------+
|substr(Feathers, 5, 1)|
+-----------------------+
|                      h|
+-----------------------+
SELECT substr('Feathers' FROM 5);
+-----------------------------------+
|substring(Feathers, 5, 2147483647)|
+-----------------------------------+
|                              hers |
+-----------------------------------+
SELECT substr('Feathers' FROM -3);
+------------------------------------+
|substring(Feathers, -3, 2147483647)|
+------------------------------------+
|                                 ers|
+------------------------------------+
SELECT substr('Feathers' FROM 5 FOR 1);
+--------------------------+
|substring(Feathers, 5, 1)|
+--------------------------+
|                         h|
+--------------------------+
-- substring
SELECT substring('Feathers', 5);
+-----------------------------------+
|substring(Feathers, 5, 2147483647)|
+-----------------------------------+
|                              hers |
+-----------------------------------+
SELECT substring('Feathers', -3);
+------------------------------------+
|substring(Feathers, -3, 2147483647)|
+------------------------------------+
|                                 ers|
+------------------------------------+
SELECT substring('Feathers', 5, 1);
+--------------------------+
|substring(Feathers, 5, 1)|
+--------------------------+
|                         h|
+--------------------------+
SELECT substring('Feathers' FROM 5);
+-----------------------------------+
|substring(Feathers, 5, 2147483647)|
+-----------------------------------+
|                              hers |
+-----------------------------------+
SELECT substring('Feathers' FROM -3);
+------------------------------------+
|substring(Feathers, -3, 2147483647)|
+------------------------------------+
|                                 ers|
+------------------------------------+
SELECT substring('Feathers' FROM 5 FOR 1);
+--------------------------+
|substring(Feathers, 5, 1)|
+--------------------------+
|                         h|
+--------------------------+
-- substring_index
SELECT substring_index('www.apache.org', '.', 2);
+-------------------------------------+
|substring_index(www.apache.org, ., 2)|
+-------------------------------------+
|                           www.apache|
+-------------------------------------+
-- to_binary
SELECT to_binary('abc', 'utf-8');
+---------------------+
|to_binary(abc, utf-8)|
+---------------------+
|           [61 62 63]|
+---------------------+
-- to_char
SELECT to_char(454, '999');
+-----------------+
|to_char(454, 999)|
+-----------------+
|              454|
+-----------------+
SELECT to_char(454.00, '000D00');
+-----------------------+
|to_char(454.00, 000D00)|
+-----------------------+
|                 454.00|
+-----------------------+
SELECT to_char(12454, '99G999');
+----------------------+
|to_char(12454, 99G999)|
+----------------------+
|                12,454|
+----------------------+
SELECT to_char(78.12, '$99.99');
+----------------------+
|to_char(78.12, $99.99)|
+----------------------+
|                $78.12|
+----------------------+
SELECT to_char(-12454.8, '99G999D9S');
+----------------------------+
|to_char(-12454.8, 99G999D9S)|
+----------------------------+
|                   12,454.8-|
+----------------------------+
-- to_number
SELECT to_number('454', '999');
+-------------------+
|to_number(454, 999)|
+-------------------+
|                454|
+-------------------+
SELECT to_number('454.00', '000.00');
+-------------------------+
|to_number(454.00, 000.00)|
+-------------------------+
|                   454.00|
+-------------------------+
SELECT to_number('12,454', '99,999');
+-------------------------+
|to_number(12,454, 99,999)|
+-------------------------+
|                    12454|
+-------------------------+
SELECT to_number('$78.12', '$99.99');
+-------------------------+
|to_number($78.12, $99.99)|
+-------------------------+
|                    78.12|
+-------------------------+
SELECT to_number('12,454.8-', '99,999.9S');
+-------------------------------+
|to_number(12,454.8-, 99,999.9S)|
+-------------------------------+
|                       -12454.8|
+-------------------------------+
-- to_varchar
SELECT to_varchar(454, '999');
+-----------------+
|to_char(454, 999)|
+-----------------+
|              454|
+-----------------+
SELECT to_varchar(454.00, '000D00');
+-----------------------+
|to_char(454.00, 000D00)|
+-----------------------+
|                 454.00|
+-----------------------+
SELECT to_varchar(12454, '99G999');
+----------------------+
|to_char(12454, 99G999)|
+----------------------+
|                12,454|
+----------------------+
SELECT to_varchar(78.12, '$99.99');
+----------------------+
|to_char(78.12, $99.99)|
+----------------------+
|                $78.12|
+----------------------+
SELECT to_varchar(-12454.8, '99G999D9S');
+----------------------------+
|to_char(-12454.8, 99G999D9S)|
+----------------------------+
|                   12,454.8-|
+----------------------------+
-- translate
SELECT translate('AaBbCc', 'abc', '123');
+---------------------------+
|translate(AaBbCc, abc, 123)|
+---------------------------+
|                     A1B2C3|
+---------------------------+
-- try_to_binary
SELECT try_to_binary('abc', 'utf-8');
+-------------------------+
|try_to_binary(abc, utf-8)|
+-------------------------+
|               [61 62 63]|
+-------------------------+
select try_to_binary('a!', 'base64');
+-------------------------+
|try_to_binary(a!, base64)|
+-------------------------+
|                     NULL|
+-------------------------+
select try_to_binary('abc', 'invalidFormat');
+---------------------------------+
|try_to_binary(abc, invalidFormat)|
+---------------------------------+
|                             NULL|
+---------------------------------+
-- try_to_number
SELECT try_to_number('454', '999');
+-----------------------+
|try_to_number(454, 999)|
+-----------------------+
|                    454|
+-----------------------+
SELECT try_to_number('454.00', '000.00');
+-----------------------------+
|try_to_number(454.00, 000.00)|
+-----------------------------+
|                       454.00|
+-----------------------------+
SELECT try_to_number('12,454', '99,999');
+-----------------------------+
|try_to_number(12,454, 99,999)|
+-----------------------------+
|                        12454|
+-----------------------------+
SELECT try_to_number('$78.12', '$99.99');
+-----------------------------+
|try_to_number($78.12, $99.99)|
+-----------------------------+
|                        78.12|
+-----------------------------+
SELECT try_to_number('12,454.8-', '99,999.9S');
+-----------------------------------+
|try_to_number(12,454.8-, 99,999.9S)|
+-----------------------------------+
|                           -12454.8|
+-----------------------------------+
-- ucase
SELECT ucase('Feathers');
+---------------+
|ucase(Feathers)|
+---------------+
|       FEATHERS|
+---------------+
-- unbase64
SELECT unbase64('U3BhcmsgU1FM');
+----------------------+
|unbase64(U3BhcmsgU1FM)|
+----------------------+
|  [53 70 61 72 6B 2...|
+----------------------+
-- upper
SELECT upper('Feathers');
+---------------+
|upper(Feathers)|
+---------------+
|       FEATHERS|
+---------------+
```

#### 日期和时间函数
<a name="supported-sql-date-time"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。


****  

| 函数 | 说明 | 
| --- | --- | 
| add\$1months(start\$1date, num\$1months) | 返回 start\$1date 之后的日期 num\$1months。 | 
| convert\$1timezone([sourceTz, ]targetTz, sourceTs) | 将不带时区 sourceTs 的时间戳从 sourceTz 时区转换为 targetTz. | 
| curdate() | 返回查询评估开始时的当前日期。在同一查询中对 curdate 的所有调用都返回相同值。 | 
| current\$1date() | 返回查询评估开始时的当前日期。在同一查询中对 current\$1date 的所有调用都返回相同值。 | 
| current\$1date | 返回查询评估开始时的当前日期。 | 
| current\$1timestamp() | 返回查询评估开始时的当前时间戳。在同一查询中对 current\$1timestamp 的所有调用都返回相同值。 | 
| current\$1timestamp | 返回查询评估开始时的当前时间戳。 | 
| current\$1timezone() | 返回当前会话的本地时区。 | 
| date\$1add(start\$1date, num\$1days) | 返回 start\$1date 之后的日期 num\$1days。 | 
| date\$1diff(endDate, startDate) | 返回从 startDate 到 endDate 的天数。 | 
| date\$1format(timestamp, fmt) | 将 timestamp 转换为符合日期格式 fmt 指定格式的字符串值。 | 
| date\$1from\$1unix\$1date(days) | 根据自 1970 年 1 月 1 日起的天数创建日期。 | 
| date\$1part(field, source) | 提取 date/timestamp 或间隔源的一部分。 | 
| date\$1sub(start\$1date, num\$1days) | 返回 start\$1date 之前的日期 num\$1days。 | 
| date\$1trunc(fmt, ts) | 返回按格式模型 fmt 指定的单位截断的时间戳 ts。 | 
| dateadd(start\$1date, num\$1days) | 返回 start\$1date 之后的日期 num\$1days。 | 
| datediff(endDate, startDate) | 返回从 startDate 到 endDate 的天数。 | 
| datepart(field, source) | 提取 date/timestamp 或间隔源的一部分。 | 
| day(date) | 返回日期/时间戳的月份日期。 | 
| dayofmonth(date) | 返回日期/时间戳的月份日期。 | 
| dayofweek(date) | 返回 date/timestamp (1 = 星期日，2 = 星期一，...，7 = 星期六) 的一周中的某一天。 | 
| dayofyear(date) | 返回日期/时间戳的年份日期。 | 
| extract(field FROM source) | 提取 date/timestamp 或间隔源的一部分。 | 
| from\$1unixtime(unix\$1time[, fmt]) | 以指定的 fmt 形式返回 unix\$1time。 | 
| from\$1utc\$1timestamp(timestamp, timezone) | 给定类似“2017-07-14 02:40:00.0”的时间戳，将其解释为 UTC 时间，并将其转换为指定时区中的时间戳进行显示。例如，“GMT\$11”将转换为“2017-07-14 03:40:00.0”。 | 
| hour(timestamp) | 返回字符串/时间戳的小时部分。 | 
| last\$1day(date) | 返回该日期所属月份的最后一天。 | 
| localtimestamp() | 返回查询评估开始时无时区的当前时间戳。在同一查询中对 localtimestamp 的所有调用都返回相同值。 | 
| localtimestamp | 返回查询评估开始时会话时区的当前本地日期时间。 | 
| make\$1date(year, month, day) | 根据年、月、日字段创建日期。 | 
| make\$1dt\$1interval([days[, hours[, mins[, secs]]]]) | 以天、小时、分钟和秒为单位制作 DayTimeIntervalType 持续时间。 | 
| make\$1interval([years[, months[, weeks[, days[, hours[, mins[, secs]]]]]]]) | 时间间隔设置为年、月、周、天、时、分和秒。 | 
| make\$1timestamp(year, month, day, hour, min, sec[, timezone]) | 根据年、月、日、时、分、秒和时区字段创建时间戳。 | 
| make\$1timestamp\$1ltz(year, month, day, hour, min, sec[, timezone]) | 根据年、月、日、时、分、秒和时区字段创建带本地时区的当前时间戳。 | 
| make\$1timestamp\$1ntz(year, month, day, hour, min, sec) | 根据年、月、日、时、分、秒字段创建本地日期时间。 | 
| make\$1ym\$1interval([years[, months]]) | 根据年份、月份生成年-月区间。 | 
| minute(timestamp) | 返回字符串/时间戳的分钟部分。 | 
| month(date) | 返回日期/时间戳的月份部分。 | 
| months\$1between(timestamp1, timestamp2[, roundOff]) | 如果 timestamp1 晚于 timestamp2，则结果为正。如果 timestamp1 和 timestamp2 在同一天，或两者均为月末最后一天，则忽略具体日期时间。否则，差值将按每月 31 天计算，并四舍五入至 8 位小数，除非 roundOff=false。 | 
| next\$1day(start\$1date, day\$1of\$1week) | 返回第一个晚于 start\$1date 且名称如指定的日期。如果至少一个输入参数为 NULL，则该函数返回 NULL。 | 
| now() | 返回查询评估开始时的当前时间戳。 | 
| quarter(date) | 返回日期所属的季度，范围为 1 到 4。 | 
| second(timestamp) | 返回字符串/时间戳的秒钟部分。 | 
| session\$1window(time\$1column, gap\$1duration) | 根据指定时间戳生成会话窗口，该时间戳用于确定列和间隔持续时间。有关详细说明和示例，请参阅《结构化流处理指南》文档中的“时间窗口类型”部分。 | 
| timestamp\$1micros(microseconds) | 根据自 UTC epoch 起的微秒数创建时间戳。 | 
| timestamp\$1millis(milliseconds) | 根据自 UTC epoch 起的毫秒数创建时间戳。 | 
| timestamp\$1seconds(seconds) | 根据自 UTC epoch 起的秒数（可以是小数）创建时间戳。 | 
| to\$1date(date\$1str[, fmt]) | 将使用 fmt 表达式的 date\$1str 表达式解析为日期。输入无效时返回 null。默认情况下，如果省略 fmt，则遵循转换规则转换为日期。 | 
| to\$1timestamp(timestamp\$1str[, fmt]) | 将使用 fmt 表达式的 timestamp\$1str 表达式解析为时间戳。输入无效时返回 null。默认情况下，如果省略 fmt，则遵循转换规则转换为时间戳。 | 
| to\$1timestamp\$1ltz(timestamp\$1str[, fmt]) | 将使用 fmt 表达式的 timestamp\$1str 表达式解析为使用本地时区的时间戳。输入无效时返回 null。默认情况下，如果省略 fmt，则遵循转换规则转换为时间戳。 | 
| to\$1timestamp\$1ntz(timestamp\$1str[, fmt]) | 将使用 fmt 表达式的 timestamp\$1str 表达式解析为无时区的时间戳。输入无效时返回 null。默认情况下，如果省略 fmt，则遵循转换规则转换为时间戳。 | 
| to\$1unix\$1timestamp(timeExp[, fmt]) | 返回给定时间的 UNIX 时间戳。 | 
| to\$1utc\$1timestamp(timestamp, timezone) | 给定类似“2017-07-14 02:40:00.0”的时间戳，将其解释为给定时区中的时间，并将其转换为 UTC 中的时间戳进行显示。例如，“GMT\$11”将转换为“2017-07-14 01:40:00.0”。 | 
| trunc(date, fmt) | 返回 date，其中日期的时间部分按格式模型 fmt 指定的单位进行截断。 | 
| try\$1to\$1timestamp(timestamp\$1str[, fmt]) | 将使用 fmt 表达式的 timestamp\$1str 表达式解析为时间戳。 | 
| unix\$1date(date) | 返回自 1970 年 1 月 1 日起经过的天数。 | 
| unix\$1micros(timestamp) | 返回自 1970-01-01 00:00:00 UTC 起经过的微秒数。 | 
| unix\$1millis(timestamp) | 返回自 1970-01-01 00:00:00 UTC 起经过的毫秒数。截断更高精度的数值。 | 
| unix\$1seconds(timestamp) | 返回自 1970-01-01 00:00:00 UTC 起经过的秒数。截断更高精度的数值。 | 
| unix\$1timestamp([timeExp[, fmt]]) | 返回当前或指定时间的 UNIX 时间戳。 | 
| weekday(date) | 返回 date/timestamp (0 = 星期一，1 = 星期二，...，6 = 星期日) 的一周中的某一天。 | 
| weekofyear(date) | 返回给定日期所在年份的星期。一周以星期一为起点开始计算，第 1 周即指首个超过 3 天的完整周。 | 
| window(time\$1column, window\$1duration[, slide\$1duration[, start\$1time]]) | 将行按指定列的时间戳划分为一个或多个时间窗口。时间窗口起始点包含在内，但终点不包含在内。例如，12:05 将位于窗口 [12:05,12:10) 内，但不在 [12:00,12:05) 之内。时间窗口支持微秒级精度。不支持以月为单位的时间窗口。有关详细说明和示例，请参阅《结构化流处理指南》文档中的“事件时间窗口操作”部分。 | 
| window\$1time(window\$1column) | 从 time/session 窗口列中提取时间值，该值可用于窗口的事件时间值。提取的时间为 (window.end - 1)，这反映出聚合窗口具有排他性上限——[start, end)。有关详细说明和示例，请参阅《结构化流处理指南》文档中的“事件时间窗口操作”部分。 | 
| year(date) | 返回日期/时间戳的年份部分。 | 

**示例**

```
-- add_months
SELECT add_months('2016-08-31', 1);
+-------------------------+
|add_months(2016-08-31, 1)|
+-------------------------+
|               2016-09-30|
+-------------------------+
-- convert_timezone
SELECT convert_timezone('Europe/Brussels', 'America/Los_Angeles', timestamp_ntz'2021-12-06 00:00:00');
+-------------------------------------------------------------------------------------------+
|convert_timezone(Europe/Brussels, America/Los_Angeles, TIMESTAMP_NTZ '2021-12-06 00:00:00')|
+-------------------------------------------------------------------------------------------+
|                                                                        2021-12-05 15:00:00|
+-------------------------------------------------------------------------------------------+
SELECT convert_timezone('Europe/Brussels', timestamp_ntz'2021-12-05 15:00:00');
+------------------------------------------------------------------------------------------+
|convert_timezone(current_timezone(), Europe/Brussels, TIMESTAMP_NTZ '2021-12-05 15:00:00')|
+------------------------------------------------------------------------------------------+
|                                                                       2021-12-05 07:00:00|
+------------------------------------------------------------------------------------------+
-- curdate
SELECT curdate();
+--------------+
|current_date()|
+--------------+
|    2024-02-24|
+--------------+
-- current_date
SELECT current_date();
+--------------+
|current_date()|
+--------------+
|    2024-02-24|
+--------------+
SELECT current_date;
+--------------+
|current_date()|
+--------------+
|    2024-02-24|
+--------------+
-- current_timestamp
SELECT current_timestamp();
+--------------------+
| current_timestamp()|
+--------------------+
|2024-02-24 16:36:...|
+--------------------+
SELECT current_timestamp;
+--------------------+
| current_timestamp()|
+--------------------+
|2024-02-24 16:36:...|
+--------------------+
-- current_timezone
SELECT current_timezone();
+------------------+
|current_timezone()|
+------------------+
|        Asia/Seoul|
+------------------+
-- date_add
SELECT date_add('2016-07-30', 1);
+-----------------------+
|date_add(2016-07-30, 1)|
+-----------------------+
|             2016-07-31|
+-----------------------+
-- date_diff
SELECT date_diff('2009-07-31', '2009-07-30');
+---------------------------------+
|date_diff(2009-07-31, 2009-07-30)|
+---------------------------------+
|                                1|
+---------------------------------+
SELECT date_diff('2009-07-30', '2009-07-31');
+---------------------------------+
|date_diff(2009-07-30, 2009-07-31)|
+---------------------------------+
|                               -1|
+---------------------------------+
-- date_format
SELECT date_format('2016-04-08', 'y');
+--------------------------+
|date_format(2016-04-08, y)|
+--------------------------+
|                      2016|
+--------------------------+
-- date_from_unix_date
SELECT date_from_unix_date(1);
+----------------------+
|date_from_unix_date(1)|
+----------------------+
|            1970-01-02|
+----------------------+
-- date_part
SELECT date_part('YEAR', TIMESTAMP '2019-08-12 01:00:00.123456');
+-------------------------------------------------------+
|date_part(YEAR, TIMESTAMP '2019-08-12 01:00:00.123456')|
+-------------------------------------------------------+
|                                                   2019|
+-------------------------------------------------------+
SELECT date_part('week', timestamp'2019-08-12 01:00:00.123456');
+-------------------------------------------------------+
|date_part(week, TIMESTAMP '2019-08-12 01:00:00.123456')|
+-------------------------------------------------------+
|                                                     33|
+-------------------------------------------------------+
SELECT date_part('doy', DATE'2019-08-12');
+---------------------------------+
|date_part(doy, DATE '2019-08-12')|
+---------------------------------+
|                              224|
+---------------------------------+
SELECT date_part('SECONDS', timestamp'2019-10-01 00:00:01.000001');
+----------------------------------------------------------+
|date_part(SECONDS, TIMESTAMP '2019-10-01 00:00:01.000001')|
+----------------------------------------------------------+
|                                                  1.000001|
+----------------------------------------------------------+
SELECT date_part('days', interval 5 days 3 hours 7 minutes);
+-------------------------------------------------+
|date_part(days, INTERVAL '5 03:07' DAY TO MINUTE)|
+-------------------------------------------------+
|                                                5|
+-------------------------------------------------+
SELECT date_part('seconds', interval 5 hours 30 seconds 1 milliseconds 1 microseconds);
+-------------------------------------------------------------+
|date_part(seconds, INTERVAL '05:00:30.001001' HOUR TO SECOND)|
+-------------------------------------------------------------+
|                                                    30.001001|
+-------------------------------------------------------------+
SELECT date_part('MONTH', INTERVAL '2021-11' YEAR TO MONTH);
+--------------------------------------------------+
|date_part(MONTH, INTERVAL '2021-11' YEAR TO MONTH)|
+--------------------------------------------------+
|                                                11|
+--------------------------------------------------+
SELECT date_part('MINUTE', INTERVAL '123 23:55:59.002001' DAY TO SECOND);
+---------------------------------------------------------------+
|date_part(MINUTE, INTERVAL '123 23:55:59.002001' DAY TO SECOND)|
+---------------------------------------------------------------+
|                                                             55|
+---------------------------------------------------------------+
-- date_sub
SELECT date_sub('2016-07-30', 1);
+-----------------------+
|date_sub(2016-07-30, 1)|
+-----------------------+
|             2016-07-29|
+-----------------------+
-- date_trunc
SELECT date_trunc('YEAR', '2015-03-05T09:32:05.359');
+-----------------------------------------+
|date_trunc(YEAR, 2015-03-05T09:32:05.359)|
+-----------------------------------------+
|                      2015-01-01 00:00:00|
+-----------------------------------------+
SELECT date_trunc('MM', '2015-03-05T09:32:05.359');
+---------------------------------------+
|date_trunc(MM, 2015-03-05T09:32:05.359)|
+---------------------------------------+
|                    2015-03-01 00:00:00|
+---------------------------------------+
SELECT date_trunc('DD', '2015-03-05T09:32:05.359');
+---------------------------------------+
|date_trunc(DD, 2015-03-05T09:32:05.359)|
+---------------------------------------+
|                    2015-03-05 00:00:00|
+---------------------------------------+
SELECT date_trunc('HOUR', '2015-03-05T09:32:05.359');
+-----------------------------------------+
|date_trunc(HOUR, 2015-03-05T09:32:05.359)|
+-----------------------------------------+
|                      2015-03-05 09:00:00|
+-----------------------------------------+
SELECT date_trunc('MILLISECOND', '2015-03-05T09:32:05.123456');
+---------------------------------------------------+
|date_trunc(MILLISECOND, 2015-03-05T09:32:05.123456)|
+---------------------------------------------------+
|                               2015-03-05 09:32:...|
+---------------------------------------------------+
-- dateadd
SELECT dateadd('2016-07-30', 1);
+-----------------------+
|date_add(2016-07-30, 1)|
+-----------------------+
|             2016-07-31|
+-----------------------+
-- datediff
SELECT datediff('2009-07-31', '2009-07-30');
+--------------------------------+
|datediff(2009-07-31, 2009-07-30)|
+--------------------------------+
|                               1|
+--------------------------------+
SELECT datediff('2009-07-30', '2009-07-31');
+--------------------------------+
|datediff(2009-07-30, 2009-07-31)|
+--------------------------------+
|                              -1|
+--------------------------------+
-- datepart
SELECT datepart('YEAR', TIMESTAMP '2019-08-12 01:00:00.123456');
+----------------------------------------------------------+
|datepart(YEAR FROM TIMESTAMP '2019-08-12 01:00:00.123456')|
+----------------------------------------------------------+
|                                                      2019|
+----------------------------------------------------------+
SELECT datepart('week', timestamp'2019-08-12 01:00:00.123456');
+----------------------------------------------------------+
|datepart(week FROM TIMESTAMP '2019-08-12 01:00:00.123456')|
+----------------------------------------------------------+
|                                                        33|
+----------------------------------------------------------+
SELECT datepart('doy', DATE'2019-08-12');
+------------------------------------+
|datepart(doy FROM DATE '2019-08-12')|
+------------------------------------+
|                                 224|
+------------------------------------+
SELECT datepart('SECONDS', timestamp'2019-10-01 00:00:01.000001');
+-------------------------------------------------------------+
|datepart(SECONDS FROM TIMESTAMP '2019-10-01 00:00:01.000001')|
+-------------------------------------------------------------+
|                                                     1.000001|
+-------------------------------------------------------------+
SELECT datepart('days', interval 5 days 3 hours 7 minutes);
+----------------------------------------------------+
|datepart(days FROM INTERVAL '5 03:07' DAY TO MINUTE)|
+----------------------------------------------------+
|                                                   5|
+----------------------------------------------------+
SELECT datepart('seconds', interval 5 hours 30 seconds 1 milliseconds 1 microseconds);
+----------------------------------------------------------------+
|datepart(seconds FROM INTERVAL '05:00:30.001001' HOUR TO SECOND)|
+----------------------------------------------------------------+
|                                                       30.001001|
+----------------------------------------------------------------+
SELECT datepart('MONTH', INTERVAL '2021-11' YEAR TO MONTH);
+-----------------------------------------------------+
|datepart(MONTH FROM INTERVAL '2021-11' YEAR TO MONTH)|
+-----------------------------------------------------+
|                                                   11|
+-----------------------------------------------------+
SELECT datepart('MINUTE', INTERVAL '123 23:55:59.002001' DAY TO SECOND);
+------------------------------------------------------------------+
|datepart(MINUTE FROM INTERVAL '123 23:55:59.002001' DAY TO SECOND)|
+------------------------------------------------------------------+
|                                                                55|
+------------------------------------------------------------------+
-- day
SELECT day('2009-07-30');
+---------------+
|day(2009-07-30)|
+---------------+
|             30|
+---------------+
-- dayofmonth
SELECT dayofmonth('2009-07-30');
+----------------------+
|dayofmonth(2009-07-30)|
+----------------------+
|                    30|
+----------------------+
-- dayofweek
SELECT dayofweek('2009-07-30');
+---------------------+
|dayofweek(2009-07-30)|
+---------------------+
|                    5|
+---------------------+
-- dayofyear
SELECT dayofyear('2016-04-09');
+---------------------+
|dayofyear(2016-04-09)|
+---------------------+
|                  100|
+---------------------+
-- extract
SELECT extract(YEAR FROM TIMESTAMP '2019-08-12 01:00:00.123456');
+---------------------------------------------------------+
|extract(YEAR FROM TIMESTAMP '2019-08-12 01:00:00.123456')|
+---------------------------------------------------------+
|                                                     2019|
+---------------------------------------------------------+
SELECT extract(week FROM timestamp'2019-08-12 01:00:00.123456');
+---------------------------------------------------------+
|extract(week FROM TIMESTAMP '2019-08-12 01:00:00.123456')|
+---------------------------------------------------------+
|                                                       33|
+---------------------------------------------------------+
SELECT extract(doy FROM DATE'2019-08-12');
+-----------------------------------+
|extract(doy FROM DATE '2019-08-12')|
+-----------------------------------+
|                                224|
+-----------------------------------+
SELECT extract(SECONDS FROM timestamp'2019-10-01 00:00:01.000001');
+------------------------------------------------------------+
|extract(SECONDS FROM TIMESTAMP '2019-10-01 00:00:01.000001')|
+------------------------------------------------------------+
|                                                    1.000001|
+------------------------------------------------------------+
SELECT extract(days FROM interval 5 days 3 hours 7 minutes);
+---------------------------------------------------+
|extract(days FROM INTERVAL '5 03:07' DAY TO MINUTE)|
+---------------------------------------------------+
|                                                  5|
+---------------------------------------------------+
SELECT extract(seconds FROM interval 5 hours 30 seconds 1 milliseconds 1 microseconds);
+---------------------------------------------------------------+
|extract(seconds FROM INTERVAL '05:00:30.001001' HOUR TO SECOND)|
+---------------------------------------------------------------+
|                                                      30.001001|
+---------------------------------------------------------------+
SELECT extract(MONTH FROM INTERVAL '2021-11' YEAR TO MONTH);
+----------------------------------------------------+
|extract(MONTH FROM INTERVAL '2021-11' YEAR TO MONTH)|
+----------------------------------------------------+
|                                                  11|
+----------------------------------------------------+
SELECT extract(MINUTE FROM INTERVAL '123 23:55:59.002001' DAY TO SECOND);
+-----------------------------------------------------------------+
|extract(MINUTE FROM INTERVAL '123 23:55:59.002001' DAY TO SECOND)|
+-----------------------------------------------------------------+
|                                                               55|
+-----------------------------------------------------------------+
-- from_unixtime
SELECT from_unixtime(0, 'yyyy-MM-dd HH:mm:ss');
+-------------------------------------+
|from_unixtime(0, yyyy-MM-dd HH:mm:ss)|
+-------------------------------------+
|                  1970-01-01 09:00:00|
+-------------------------------------+
SELECT from_unixtime(0);
+-------------------------------------+
|from_unixtime(0, yyyy-MM-dd HH:mm:ss)|
+-------------------------------------+
|                  1970-01-01 09:00:00|
+-------------------------------------+
-- from_utc_timestamp
SELECT from_utc_timestamp('2016-08-31', 'Asia/Seoul');
+------------------------------------------+
|from_utc_timestamp(2016-08-31, Asia/Seoul)|
+------------------------------------------+
|                       2016-08-31 09:00:00|
+------------------------------------------+
-- hour
SELECT hour('2009-07-30 12:58:59');
+-------------------------+
|hour(2009-07-30 12:58:59)|
+-------------------------+
|                       12|
+-------------------------+
-- last_day
SELECT last_day('2009-01-12');
+--------------------+
|last_day(2009-01-12)|
+--------------------+
|          2009-01-31|
+--------------------+
-- localtimestamp
SELECT localtimestamp();
+--------------------+
|    localtimestamp()|
+--------------------+
|2024-02-24 16:36:...|
+--------------------+
-- make_date
SELECT make_date(2013, 7, 15);
+----------------------+
|make_date(2013, 7, 15)|
+----------------------+
|            2013-07-15|
+----------------------+
SELECT make_date(2019, 7, NULL);
+------------------------+
|make_date(2019, 7, NULL)|
+------------------------+
|                    NULL|
+------------------------+
-- make_dt_interval
SELECT make_dt_interval(1, 12, 30, 01.001001);
+-------------------------------------+
|make_dt_interval(1, 12, 30, 1.001001)|
+-------------------------------------+
|                 INTERVAL '1 12:30...|
+-------------------------------------+
SELECT make_dt_interval(2);
+-----------------------------------+
|make_dt_interval(2, 0, 0, 0.000000)|
+-----------------------------------+
|               INTERVAL '2 00:00...|
+-----------------------------------+
SELECT make_dt_interval(100, null, 3);
+----------------------------------------+
|make_dt_interval(100, NULL, 3, 0.000000)|
+----------------------------------------+
|                                    NULL|
+----------------------------------------+
-- make_interval
SELECT make_interval(100, 11, 1, 1, 12, 30, 01.001001);
+----------------------------------------------+
|make_interval(100, 11, 1, 1, 12, 30, 1.001001)|
+----------------------------------------------+
|                          100 years 11 mont...|
+----------------------------------------------+
SELECT make_interval(100, null, 3);
+----------------------------------------------+
|make_interval(100, NULL, 3, 0, 0, 0, 0.000000)|
+----------------------------------------------+
|                                          NULL|
+----------------------------------------------+
SELECT make_interval(0, 1, 0, 1, 0, 0, 100.000001);
+-------------------------------------------+
|make_interval(0, 1, 0, 1, 0, 0, 100.000001)|
+-------------------------------------------+
|                       1 months 1 days 1...|
+-------------------------------------------+
-- make_timestamp
SELECT make_timestamp(2014, 12, 28, 6, 30, 45.887);
+-------------------------------------------+
|make_timestamp(2014, 12, 28, 6, 30, 45.887)|
+-------------------------------------------+
|                       2014-12-28 06:30:...|
+-------------------------------------------+
SELECT make_timestamp(2014, 12, 28, 6, 30, 45.887, 'CET');
+------------------------------------------------+
|make_timestamp(2014, 12, 28, 6, 30, 45.887, CET)|
+------------------------------------------------+
|                            2014-12-28 14:30:...|
+------------------------------------------------+
SELECT make_timestamp(2019, 6, 30, 23, 59, 60);
+---------------------------------------+
|make_timestamp(2019, 6, 30, 23, 59, 60)|
+---------------------------------------+
|                    2019-07-01 00:00:00|
+---------------------------------------+
SELECT make_timestamp(2019, 6, 30, 23, 59, 1);
+--------------------------------------+
|make_timestamp(2019, 6, 30, 23, 59, 1)|
+--------------------------------------+
|                   2019-06-30 23:59:01|
+--------------------------------------+
SELECT make_timestamp(null, 7, 22, 15, 30, 0);
+--------------------------------------+
|make_timestamp(NULL, 7, 22, 15, 30, 0)|
+--------------------------------------+
|                                  NULL|
+--------------------------------------+
-- make_timestamp_ltz
SELECT make_timestamp_ltz(2014, 12, 28, 6, 30, 45.887);
+-----------------------------------------------+
|make_timestamp_ltz(2014, 12, 28, 6, 30, 45.887)|
+-----------------------------------------------+
|                           2014-12-28 06:30:...|
+-----------------------------------------------+
SELECT make_timestamp_ltz(2014, 12, 28, 6, 30, 45.887, 'CET');
+----------------------------------------------------+
|make_timestamp_ltz(2014, 12, 28, 6, 30, 45.887, CET)|
+----------------------------------------------------+
|                                2014-12-28 14:30:...|
+----------------------------------------------------+
SELECT make_timestamp_ltz(2019, 6, 30, 23, 59, 60);
+-------------------------------------------+
|make_timestamp_ltz(2019, 6, 30, 23, 59, 60)|
+-------------------------------------------+
|                        2019-07-01 00:00:00|
+-------------------------------------------+
SELECT make_timestamp_ltz(null, 7, 22, 15, 30, 0);
+------------------------------------------+
|make_timestamp_ltz(NULL, 7, 22, 15, 30, 0)|
+------------------------------------------+
|                                      NULL|
+------------------------------------------+
-- make_timestamp_ntz
SELECT make_timestamp_ntz(2014, 12, 28, 6, 30, 45.887);
+-----------------------------------------------+
|make_timestamp_ntz(2014, 12, 28, 6, 30, 45.887)|
+-----------------------------------------------+
|                           2014-12-28 06:30:...|
+-----------------------------------------------+
SELECT make_timestamp_ntz(2019, 6, 30, 23, 59, 60);
+-------------------------------------------+
|make_timestamp_ntz(2019, 6, 30, 23, 59, 60)|
+-------------------------------------------+
|                        2019-07-01 00:00:00|
+-------------------------------------------+
SELECT make_timestamp_ntz(null, 7, 22, 15, 30, 0);
+------------------------------------------+
|make_timestamp_ntz(NULL, 7, 22, 15, 30, 0)|
+------------------------------------------+
|                                      NULL|
+------------------------------------------+
-- make_ym_interval
SELECT make_ym_interval(1, 2);
+----------------------+
|make_ym_interval(1, 2)|
+----------------------+
|  INTERVAL '1-2' YE...|
+----------------------+
SELECT make_ym_interval(1, 0);
+----------------------+
|make_ym_interval(1, 0)|
+----------------------+
|  INTERVAL '1-0' YE...|
+----------------------+
SELECT make_ym_interval(-1, 1);
+-----------------------+
|make_ym_interval(-1, 1)|
+-----------------------+
|   INTERVAL '-0-11' ...|
+-----------------------+
SELECT make_ym_interval(2);
+----------------------+
|make_ym_interval(2, 0)|
+----------------------+
|  INTERVAL '2-0' YE...|
+----------------------+
-- minute
SELECT minute('2009-07-30 12:58:59');
+---------------------------+
|minute(2009-07-30 12:58:59)|
+---------------------------+
|                         58|
+---------------------------+
-- month
SELECT month('2016-07-30');
+-----------------+
|month(2016-07-30)|
+-----------------+
|                7|
+-----------------+
-- months_between
SELECT months_between('1997-02-28 10:30:00', '1996-10-30');
+-----------------------------------------------------+
|months_between(1997-02-28 10:30:00, 1996-10-30, true)|
+-----------------------------------------------------+
|                                           3.94959677|
+-----------------------------------------------------+
SELECT months_between('1997-02-28 10:30:00', '1996-10-30', false);
+------------------------------------------------------+
|months_between(1997-02-28 10:30:00, 1996-10-30, false)|
+------------------------------------------------------+
|                                    3.9495967741935485|
+------------------------------------------------------+
-- next_day
SELECT next_day('2015-01-14', 'TU');
+------------------------+
|next_day(2015-01-14, TU)|
+------------------------+
|              2015-01-20|
+------------------------+
-- now
SELECT now();
+--------------------+
|               now()|
+--------------------+
|2024-02-24 16:36:...|
+--------------------+
-- quarter
SELECT quarter('2016-08-31');
+-------------------+
|quarter(2016-08-31)|
+-------------------+
|                  3|
+-------------------+
-- second
SELECT second('2009-07-30 12:58:59');
+---------------------------+
|second(2009-07-30 12:58:59)|
+---------------------------+
|                         59|
+---------------------------+
-- session_window
SELECT a, session_window.start, session_window.end, count(*) as cnt FROM VALUES ('A1', '2021-01-01 00:00:00'), ('A1', '2021-01-01 00:04:30'), ('A1', '2021-01-01 00:10:00'), ('A2', '2021-01-01 00:01:00') AS tab(a, b) GROUP by a, session_window(b, '5 minutes') ORDER BY a, start;
+---+-------------------+-------------------+---+
|  a|              start|                end|cnt|
+---+-------------------+-------------------+---+
| A1|2021-01-01 00:00:00|2021-01-01 00:09:30|  2|
| A1|2021-01-01 00:10:00|2021-01-01 00:15:00|  1|
| A2|2021-01-01 00:01:00|2021-01-01 00:06:00|  1|
+---+-------------------+-------------------+---+
SELECT a, session_window.start, session_window.end, count(*) as cnt FROM VALUES ('A1', '2021-01-01 00:00:00'), ('A1', '2021-01-01 00:04:30'), ('A1', '2021-01-01 00:10:00'), ('A2', '2021-01-01 00:01:00'), ('A2', '2021-01-01 00:04:30') AS tab(a, b) GROUP by a, session_window(b, CASE WHEN a = 'A1' THEN '5 minutes' WHEN a = 'A2' THEN '1 minute' ELSE '10 minutes' END) ORDER BY a, start;
+---+-------------------+-------------------+---+
|  a|              start|                end|cnt|
+---+-------------------+-------------------+---+
| A1|2021-01-01 00:00:00|2021-01-01 00:09:30|  2|
| A1|2021-01-01 00:10:00|2021-01-01 00:15:00|  1|
| A2|2021-01-01 00:01:00|2021-01-01 00:02:00|  1|
| A2|2021-01-01 00:04:30|2021-01-01 00:05:30|  1|
+---+-------------------+-------------------+---+
-- timestamp_micros
SELECT timestamp_micros(1230219000123123);
+----------------------------------+
|timestamp_micros(1230219000123123)|
+----------------------------------+
|              2008-12-26 00:30:...|
+----------------------------------+
-- timestamp_millis
SELECT timestamp_millis(1230219000123);
+-------------------------------+
|timestamp_millis(1230219000123)|
+-------------------------------+
|           2008-12-26 00:30:...|
+-------------------------------+
-- timestamp_seconds
SELECT timestamp_seconds(1230219000);
+-----------------------------+
|timestamp_seconds(1230219000)|
+-----------------------------+
|          2008-12-26 00:30:00|
+-----------------------------+
SELECT timestamp_seconds(1230219000.123);
+---------------------------------+
|timestamp_seconds(1230219000.123)|
+---------------------------------+
|             2008-12-26 00:30:...|
+---------------------------------+
-- to_date
SELECT to_date('2009-07-30 04:17:52');
+----------------------------+
|to_date(2009-07-30 04:17:52)|
+----------------------------+
|                  2009-07-30|
+----------------------------+
SELECT to_date('2016-12-31', 'yyyy-MM-dd');
+-------------------------------+
|to_date(2016-12-31, yyyy-MM-dd)|
+-------------------------------+
|                     2016-12-31|
+-------------------------------+
-- to_timestamp
SELECT to_timestamp('2016-12-31 00:12:00');
+---------------------------------+
|to_timestamp(2016-12-31 00:12:00)|
+---------------------------------+
|              2016-12-31 00:12:00|
+---------------------------------+
SELECT to_timestamp('2016-12-31', 'yyyy-MM-dd');
+------------------------------------+
|to_timestamp(2016-12-31, yyyy-MM-dd)|
+------------------------------------+
|                 2016-12-31 00:00:00|
+------------------------------------+
-- to_timestamp_ltz
SELECT to_timestamp_ltz('2016-12-31 00:12:00');
+-------------------------------------+
|to_timestamp_ltz(2016-12-31 00:12:00)|
+-------------------------------------+
|                  2016-12-31 00:12:00|
+-------------------------------------+
SELECT to_timestamp_ltz('2016-12-31', 'yyyy-MM-dd');
+----------------------------------------+
|to_timestamp_ltz(2016-12-31, yyyy-MM-dd)|
+----------------------------------------+
|                     2016-12-31 00:00:00|
+----------------------------------------+
-- to_timestamp_ntz
SELECT to_timestamp_ntz('2016-12-31 00:12:00');
+-------------------------------------+
|to_timestamp_ntz(2016-12-31 00:12:00)|
+-------------------------------------+
|                  2016-12-31 00:12:00|
+-------------------------------------+
SELECT to_timestamp_ntz('2016-12-31', 'yyyy-MM-dd');
+----------------------------------------+
|to_timestamp_ntz(2016-12-31, yyyy-MM-dd)|
+----------------------------------------+
|                     2016-12-31 00:00:00|
+----------------------------------------+
-- to_unix_timestamp
SELECT to_unix_timestamp('2016-04-08', 'yyyy-MM-dd');
+-----------------------------------------+
|to_unix_timestamp(2016-04-08, yyyy-MM-dd)|
+-----------------------------------------+
|                               1460041200|
+-----------------------------------------+
-- to_utc_timestamp
SELECT to_utc_timestamp('2016-08-31', 'Asia/Seoul');
+----------------------------------------+
|to_utc_timestamp(2016-08-31, Asia/Seoul)|
+----------------------------------------+
|                     2016-08-30 15:00:00|
+----------------------------------------+
-- trunc
SELECT trunc('2019-08-04', 'week');
+-----------------------+
|trunc(2019-08-04, week)|
+-----------------------+
|             2019-07-29|
+-----------------------+
SELECT trunc('2019-08-04', 'quarter');
+--------------------------+
|trunc(2019-08-04, quarter)|
+--------------------------+
|                2019-07-01|
+--------------------------+
SELECT trunc('2009-02-12', 'MM');
+---------------------+
|trunc(2009-02-12, MM)|
+---------------------+
|           2009-02-01|
+---------------------+
SELECT trunc('2015-10-27', 'YEAR');
+-----------------------+
|trunc(2015-10-27, YEAR)|
+-----------------------+
|             2015-01-01|
+-----------------------+
-- try_to_timestamp
SELECT try_to_timestamp('2016-12-31 00:12:00');
+-------------------------------------+
|try_to_timestamp(2016-12-31 00:12:00)|
+-------------------------------------+
|                  2016-12-31 00:12:00|
+-------------------------------------+
SELECT try_to_timestamp('2016-12-31', 'yyyy-MM-dd');
+----------------------------------------+
|try_to_timestamp(2016-12-31, yyyy-MM-dd)|
+----------------------------------------+
|                     2016-12-31 00:00:00|
+----------------------------------------+
SELECT try_to_timestamp('foo', 'yyyy-MM-dd');
+---------------------------------+
|try_to_timestamp(foo, yyyy-MM-dd)|
+---------------------------------+
|                             NULL|
+---------------------------------+
-- unix_date
SELECT unix_date(DATE("1970-01-02"));
+---------------------+
|unix_date(1970-01-02)|
+---------------------+
|                    1|
+---------------------+
-- unix_micros
SELECT unix_micros(TIMESTAMP('1970-01-01 00:00:01Z'));
+---------------------------------+
|unix_micros(1970-01-01 00:00:01Z)|
+---------------------------------+
|                          1000000|
+---------------------------------+
-- unix_millis
SELECT unix_millis(TIMESTAMP('1970-01-01 00:00:01Z'));
+---------------------------------+
|unix_millis(1970-01-01 00:00:01Z)|
+---------------------------------+
|                             1000|
+---------------------------------+
-- unix_seconds
SELECT unix_seconds(TIMESTAMP('1970-01-01 00:00:01Z'));
+----------------------------------+
|unix_seconds(1970-01-01 00:00:01Z)|
+----------------------------------+
|                                 1|
+----------------------------------+
-- unix_timestamp
SELECT unix_timestamp();
+--------------------------------------------------------+
|unix_timestamp(current_timestamp(), yyyy-MM-dd HH:mm:ss)|
+--------------------------------------------------------+
|                                              1708760216|
+--------------------------------------------------------+
SELECT unix_timestamp('2016-04-08', 'yyyy-MM-dd');
+--------------------------------------+
|unix_timestamp(2016-04-08, yyyy-MM-dd)|
+--------------------------------------+
|                            1460041200|
+--------------------------------------+
-- weekday
SELECT weekday('2009-07-30');
+-------------------+
|weekday(2009-07-30)|
+-------------------+
|                  3|
+-------------------+
-- weekofyear
SELECT weekofyear('2008-02-20');
+----------------------+
|weekofyear(2008-02-20)|
+----------------------+
|                     8|
+----------------------+
-- window
SELECT a, window.start, window.end, count(*) as cnt FROM VALUES ('A1', '2021-01-01 00:00:00'), ('A1', '2021-01-01 00:04:30'), ('A1', '2021-01-01 00:06:00'), ('A2', '2021-01-01 00:01:00') AS tab(a, b) GROUP by a, window(b, '5 minutes') ORDER BY a, start;
+---+-------------------+-------------------+---+
|  a|              start|                end|cnt|
+---+-------------------+-------------------+---+
| A1|2021-01-01 00:00:00|2021-01-01 00:05:00|  2|
| A1|2021-01-01 00:05:00|2021-01-01 00:10:00|  1|
| A2|2021-01-01 00:00:00|2021-01-01 00:05:00|  1|
+---+-------------------+-------------------+---+
SELECT a, window.start, window.end, count(*) as cnt FROM VALUES ('A1', '2021-01-01 00:00:00'), ('A1', '2021-01-01 00:04:30'), ('A1', '2021-01-01 00:06:00'), ('A2', '2021-01-01 00:01:00') AS tab(a, b) GROUP by a, window(b, '10 minutes', '5 minutes') ORDER BY a, start;
+---+-------------------+-------------------+---+
|  a|              start|                end|cnt|
+---+-------------------+-------------------+---+
| A1|2020-12-31 23:55:00|2021-01-01 00:05:00|  2|
| A1|2021-01-01 00:00:00|2021-01-01 00:10:00|  3|
| A1|2021-01-01 00:05:00|2021-01-01 00:15:00|  1|
| A2|2020-12-31 23:55:00|2021-01-01 00:05:00|  1|
| A2|2021-01-01 00:00:00|2021-01-01 00:10:00|  1|
+---+-------------------+-------------------+---+
-- window_time
SELECT a, window.start as start, window.end as end, window_time(window), cnt FROM (SELECT a, window, count(*) as cnt FROM VALUES ('A1', '2021-01-01 00:00:00'), ('A1', '2021-01-01 00:04:30'), ('A1', '2021-01-01 00:06:00'), ('A2', '2021-01-01 00:01:00') AS tab(a, b) GROUP by a, window(b, '5 minutes') ORDER BY a, window.start);
+---+-------------------+-------------------+--------------------+---+
|  a|              start|                end| window_time(window)|cnt|
+---+-------------------+-------------------+--------------------+---+
| A1|2021-01-01 00:00:00|2021-01-01 00:05:00|2021-01-01 00:04:...|  2|
| A1|2021-01-01 00:05:00|2021-01-01 00:10:00|2021-01-01 00:09:...|  1|
| A2|2021-01-01 00:00:00|2021-01-01 00:05:00|2021-01-01 00:04:...|  1|
+---+-------------------+-------------------+--------------------+---+
-- year
SELECT year('2016-07-30');
+----------------+
|year(2016-07-30)|
+----------------+
|            2016|
+----------------+
```

#### 聚合函数
<a name="supported-sql-aggregate"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

聚合函数对各行的值进行运算以执行数学计算，例如求和、平均 minimum/maximum 值、计数、值、标准差和估计，以及一些非数学运算。

**语法**

```
aggregate_function(input1 [, input2, ...]) FILTER (WHERE boolean_expression) 
```

**参数**
+ `boolean_expression`：指定任何评估结果为布尔值的表达式。两个或多个表达式可使用逻辑运算符（AND、OR）进行组合。

**有序集合聚合函数**

这些聚合函数采用与其他聚合函数不同的语法，用于指定对值进行排序的表达式（通常为列名）。

**语法**

```
{ PERCENTILE_CONT | PERCENTILE_DISC }(percentile) WITHIN GROUP (ORDER BY { order_by_expression [ ASC | DESC ] [ NULLS { FIRST | LAST } ] [ , ... ] }) FILTER (WHERE boolean_expression) 
```

**参数**
+ `percentile`：要查找值的百分位数。百分位数必须是介于 0.0 和 1.0 之间的常数。
+ `order_by_expression`：用于在聚合值之前对值进行排序的表达式（通常为列名）。
+ `boolean_expression`：指定任何评估结果为布尔值的表达式。两个或多个表达式可使用逻辑运算符（AND、OR）进行组合。

**示例**

```
CREATE OR REPLACE TEMPORARY VIEW basic_pays AS SELECT * FROM VALUES
('Jane Doe','Accounting',8435),
('Akua Mansa','Accounting',9998),
('John Doe','Accounting',8992),
('Juan Li','Accounting',8870),
('Carlos Salazar','Accounting',11472),
('Arnav Desai','Accounting',6627),
('Saanvi Sarkar','IT',8113),
('Shirley Rodriguez','IT',5186),
('Nikki Wolf','Sales',9181),
('Alejandro Rosalez','Sales',9441),
('Nikhil Jayashankar','Sales',6660),
('Richard Roe','Sales',10563),
('Pat Candella','SCM',10449),
('Gerard Hernandez','SCM',6949),
('Pamela Castillo','SCM',11303),
('Paulo Santos','SCM',11798),
('Jorge Souza','SCM',10586)
AS basic_pays(employee_name, department, salary);
SELECT * FROM basic_pays;
+-------------------+----------+------+
|    employee_name  |department|salary|
+-------------------+----------+------+
| Arnav Desai       |Accounting|  6627|
| Jorge Souza       |       SCM| 10586|
| Jane Doe          |Accounting|  8435|
| Nikhil Jayashankar|     Sales|  6660|
| Diego Vanauf      |     Sales| 10563|
| Carlos Salazar    |Accounting| 11472|
| Gerard Hernandez  |       SCM|  6949|
| John Doe          |Accounting|  8992|
| Nikki Wolf        |     Sales|  9181|
| Paulo Santos      |       SCM| 11798|
| Saanvi Sarkar     |        IT|  8113|
| Shirley Rodriguez |        IT|  5186|
| Pat Candella      |       SCM| 10449|
| Akua Mansa        |Accounting|  9998|
| Pamela Castillo   |       SCM| 11303|
| Alejandro Rosalez |     Sales|  9441|
| Juan Li           |Accounting|  8870|
+-------------------+----------+------+
SELECT
department,
percentile_cont(0.25) WITHIN GROUP (ORDER BY salary) AS pc1,
percentile_cont(0.25) WITHIN GROUP (ORDER BY salary) FILTER (WHERE employee_name LIKE '%Bo%') AS pc2,
percentile_cont(0.25) WITHIN GROUP (ORDER BY salary DESC) AS pc3,
percentile_cont(0.25) WITHIN GROUP (ORDER BY salary DESC) FILTER (WHERE employee_name LIKE '%Bo%') AS pc4,
percentile_disc(0.25) WITHIN GROUP (ORDER BY salary) AS pd1,
percentile_disc(0.25) WITHIN GROUP (ORDER BY salary) FILTER (WHERE employee_name LIKE '%Bo%') AS pd2,
percentile_disc(0.25) WITHIN GROUP (ORDER BY salary DESC) AS pd3,
percentile_disc(0.25) WITHIN GROUP (ORDER BY salary DESC) FILTER (WHERE employee_name LIKE '%Bo%') AS pd4
FROM basic_pays
GROUP BY department
ORDER BY department;
+----------+-------+--------+-------+--------+-----+-----+-----+-----+
|department|    pc1|     pc2|    pc3|     pc4|  pd1|  pd2|  pd3|  pd4|
+----------+-------+--------+-------+--------+-----+-----+-----+-----+
|Accounting|8543.75| 7838.25| 9746.5|10260.75| 8435| 6627| 9998|11472|
|        IT|5917.75|    NULL|7381.25|    NULL| 5186| NULL| 8113| NULL|
|     Sales|8550.75|    NULL| 9721.5|    NULL| 6660| NULL|10563| NULL|
|       SCM|10449.0|10786.25|11303.0|11460.75|10449|10449|11303|11798|
+----------+-------+--------+-------+--------+-----+-----+-----+-----+
```

#### 条件函数
<a name="supported-sql-conditional"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。


****  

| 函数 | 说明 | 
| --- | --- | 
| coalesce(expr1, expr2, ...) | 如果存在，则返回第一个非 null 参数。否则为 null。 | 
| if(expr1, expr2, expr3) | 如果 expr1 计算结果为 true，则返回 expr2；否则返回 expr3。 | 
| ifnull(expr1, expr2) | 如果 expr1 为 null，则返回 expr2，否则返回 expr1。 | 
| nanvl(expr1, expr2) | 如果不是 NaN，则返回 expr1，否则返回 expr2。 | 
| nullif(expr1, expr2) | 如果 expr1 等于 expr2，则返回 null，否则返回 expr1。 | 
| nvl(expr1, expr2) | 如果 expr1 为 null，则返回 expr2，否则返回 expr1。 | 
| nvl2(expr1, expr2, expr3) | 如果 expr1 不为 null，则返回 expr2，否则返回 expr3。 | 
| CASE WHEN expr1 THEN expr2 [WHEN expr3 THEN expr4]\$1 [ELSE expr5] END | 当 expr1 = true 时，返回 expr2；而当 expr3 = true 时，返回 expr4；否则返回 expr5。 | 

**示例**

```
-- coalesce
SELECT coalesce(NULL, 1, NULL);
+-----------------------+
|coalesce(NULL, 1, NULL)|
+-----------------------+
|                      1|
+-----------------------+
-- if
SELECT if(1 < 2, 'a', 'b');
+-------------------+
|(IF((1 < 2), a, b))|
+-------------------+
|                  a|
+-------------------+
-- ifnull
SELECT ifnull(NULL, array('2'));
+----------------------+
|ifnull(NULL, array(2))|
+----------------------+
|                   [2]|
+----------------------+
-- nanvl
SELECT nanvl(cast('NaN' as double), 123);
+-------------------------------+
|nanvl(CAST(NaN AS DOUBLE), 123)|
+-------------------------------+
|                          123.0|
+-------------------------------+
-- nullif
SELECT nullif(2, 2);
+------------+
|nullif(2, 2)|
+------------+
|        NULL|
+------------+
-- nvl
SELECT nvl(NULL, array('2'));
+-------------------+
|nvl(NULL, array(2))|
+-------------------+
|                [2]|
+-------------------+
-- nvl2
SELECT nvl2(NULL, 2, 1);
+----------------+
|nvl2(NULL, 2, 1)|
+----------------+
|               1|
+----------------+
-- when
SELECT CASE WHEN 1 > 0 THEN 1 WHEN 2 > 0 THEN 2.0 ELSE 1.2 END;
+-----------------------------------------------------------+
|CASE WHEN (1 > 0) THEN 1 WHEN (2 > 0) THEN 2.0 ELSE 1.2 END|
+-----------------------------------------------------------+
|                                                        1.0|
+-----------------------------------------------------------+
SELECT CASE WHEN 1 < 0 THEN 1 WHEN 2 > 0 THEN 2.0 ELSE 1.2 END;
+-----------------------------------------------------------+
|CASE WHEN (1 < 0) THEN 1 WHEN (2 > 0) THEN 2.0 ELSE 1.2 END|
+-----------------------------------------------------------+
|                                                        2.0|
+-----------------------------------------------------------+
SELECT CASE WHEN 1 < 0 THEN 1 WHEN 2 < 0 THEN 2.0 END;
+--------------------------------------------------+
|CASE WHEN (1 < 0) THEN 1 WHEN (2 < 0) THEN 2.0 END|
+--------------------------------------------------+
|                                              NULL|
+--------------------------------------------------+
```

#### JSON 函数
<a name="supported-sql-json"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。




****  

| 函数 | 说明 | 
| --- | --- | 
| from\$1json(jsonStr, schema[, options]) | 返回包含给定 `jsonStr` 和 `schema` 的结构值。 | 
| get\$1json\$1object(json\$1txt, path) | 从 `path` 中提取 json 对象。 | 
| json\$1array\$1length(jsonArray) | 返回最外层 JSON 数组中的元素数量。 | 
| json\$1object\$1keys(json\$1object) | 以数组形式返回最外层 JSON 对象的所有键。 | 
| json\$1tuple(jsonStr, p1, p2, ..., pn) | 返回与函数 get\$1json\$1object 类似的元组，但接受多个名称。所有输入参数和输出列类型均为字符串。 | 
| schema\$1of\$1json(json[, options]) | 返回以 JSON 字符串的 DDL 格式表示的架构。 | 
| to\$1json(expr[, options]) | 返回包含给定结构值的 JSON 字符串 | 

**示例**

```
-- from_json
SELECT from_json('{"a":1, "b":0.8}', 'a INT, b DOUBLE');
+---------------------------+
| from_json({"a":1, "b":0.8}) |
+---------------------------+
| {1, 0.8}                  |
+---------------------------+

SELECT from_json('{"time":"26/08/2015"}', 'time Timestamp', map('timestampFormat', 'dd/MM/yyyy'));
+--------------------------------+
| from_json({"time":"26/08/2015"}) |
+--------------------------------+
| {2015-08-26 00:00...           |
+--------------------------------+

SELECT from_json('{"teacher": "Alice", "student": [{"name": "Bob", "rank": 1}, {"name": "Charlie", "rank": 2}]}', 'STRUCT<teacher: STRING, student: ARRAY<STRUCT<name: STRING, rank: INT>>>');
+--------------------------------------------------------------------------------------------------------+
| from_json({"teacher": "Alice", "student": [{"name": "Bob", "rank": 1}, {"name": "Charlie", "rank": 2}]}) |
+--------------------------------------------------------------------------------------------------------+
| {Alice, [{Bob, 1}...                                                                                   |
+--------------------------------------------------------------------------------------------------------+

-- get_json_object
SELECT get_json_object('{"a":"b"}', '$.a');
+-------------------------------+
| get_json_object({"a":"b"}, $.a) |
+-------------------------------+
| b                             |
+-------------------------------+

-- json_array_length
SELECT json_array_length('[1,2,3,4]');
+----------------------------+
| json_array_length([1,2,3,4]) |
+----------------------------+
| 4                          |
+----------------------------+

SELECT json_array_length('[1,2,3,{"f1":1,"f2":[5,6]},4]');
+------------------------------------------------+
| json_array_length([1,2,3,{"f1":1,"f2":[5,6]},4]) |
+------------------------------------------------+
| 5                                              |
+------------------------------------------------+

SELECT json_array_length('[1,2');
+-----------------------+
| json_array_length([1,2) |
+-----------------------+
| NULL                  |
+-----------------------+

-- json_object_keys
SELECT json_object_keys('{}');
+--------------------+
| json_object_keys({}) |
+--------------------+
| []                 |
+--------------------+

SELECT json_object_keys('{"key": "value"}');
+----------------------------------+
| json_object_keys({"key": "value"}) |
+----------------------------------+
| [key]                            |
+----------------------------------+

SELECT json_object_keys('{"f1":"abc","f2":{"f3":"a", "f4":"b"}}');
+--------------------------------------------------------+
| json_object_keys({"f1":"abc","f2":{"f3":"a", "f4":"b"}}) |
+--------------------------------------------------------+
| [f1, f2]                                               |
+--------------------------------------------------------+

-- json_tuple
SELECT json_tuple('{"a":1, "b":2}', 'a', 'b');
+---+---+
| c0| c1|
+---+---+
|  1|  2|
+---+---+

-- schema_of_json
SELECT schema_of_json('[{"col":0}]');
+---------------------------+
| schema_of_json([{"col":0}]) |
+---------------------------+
| ARRAY<STRUCT<col:...      |
+---------------------------+

SELECT schema_of_json('[{"col":01}]', map('allowNumericLeadingZeros', 'true'));
+----------------------------+
| schema_of_json([{"col":01}]) |
+----------------------------+
| ARRAY<STRUCT<col:...       |
+----------------------------+

-- to_json
SELECT to_json(named_struct('a', 1, 'b', 2));
+---------------------------------+
| to_json(named_struct(a, 1, b, 2)) |
+---------------------------------+
| {"a":1,"b":2}                   |
+---------------------------------+

SELECT to_json(named_struct('time', to_timestamp('2015-08-26', 'yyyy-MM-dd')), map('timestampFormat', 'dd/MM/yyyy'));
+-----------------------------------------------------------------+
| to_json(named_struct(time, to_timestamp(2015-08-26, yyyy-MM-dd))) |
+-----------------------------------------------------------------+
| {"time":"26/08/20...                                            |
+-----------------------------------------------------------------+

SELECT to_json(array(named_struct('a', 1, 'b', 2)));
+----------------------------------------+
| to_json(array(named_struct(a, 1, b, 2))) |
+----------------------------------------+
| [{"a":1,"b":2}]                        |
+----------------------------------------+

SELECT to_json(map('a', named_struct('b', 1)));
+-----------------------------------+
| to_json(map(a, named_struct(b, 1))) |
+-----------------------------------+
| {"a":{"b":1}}                     |
+-----------------------------------+

SELECT to_json(map(named_struct('a', 1),named_struct('b', 2)));
+----------------------------------------------------+
| to_json(map(named_struct(a, 1), named_struct(b, 2))) |
+----------------------------------------------------+
| {"[1]":{"b":2}}                                    |
+----------------------------------------------------+

SELECT to_json(map('a', 1));
+------------------+
| to_json(map(a, 1)) |
+------------------+
| {"a":1}          |
+------------------+

SELECT to_json(array(map('a', 1)));
+-------------------------+
| to_json(array(map(a, 1))) |
+-------------------------+
| [{"a":1}]               |
+-------------------------+
```

#### 数组函数
<a name="supported-sql-array"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。


****  

| 函数 | 说明 | 
| --- | --- | 
| array(expr, ...) | 返回包含给定元素的数组。 | 
| array\$1append(array, element) | 将元素添加到作为第一个参数传递的数组末尾。元素类型应与数组中元素的类型相似。Null 元素也要附加到数组中。但如果传递的数组为 NULL，则输出为 NULL | 
| array\$1compact(array) | 从数组中移除 null 值。 | 
| array\$1contains(array, value) | 如果数组包含该值，则返回 true。 | 
| array\$1distinct(array) | 从数组中移除重复值。 | 
| array\$1except(array1, array2) | 返回数组，包含 array1 中的元素，但不包含 array2 中的元素，且不包含重复项。 | 
| array\$1insert(x, pos, val) | 将 val 放入数组 x 的索引位置 pos。数组索引从 1 开始。最大负索引值为 -1，此时函数会在当前最后一个元素之后插入新元素。索引大于数组大小时，在数组末尾附加数组；如果索引为负值，则在数组开头附加数组，并填充“null”元素。 | 
| array\$1intersect(array1, array2) | 返回包含 array1 和 array2 交集元素的数组，且不含重复项。 | 
| array\$1join(array, delimiter[, nullReplacement]) | 使用分隔符和可选字符串连接给定数组的元素以替换 null 值。如果未设置 nullReplacement 的值，则会筛选任何 null 值。 | 
| array\$1max(array) | 返回数组中的最大值。就 double/float 类型而言，NaN 大于任何非 NaN 元素。跳过 NULL 元素。 | 
| array\$1min(array) | 返回数组中的最小值。就 double/float 类型而言，NaN 大于任何非 NaN 元素。跳过 NULL 元素。 | 
| array\$1position(array, element) | 返回数组中第一个匹配元素的（从 1 开始）索引作为长整型数值，如果未找到匹配项，则返回 0。 | 
| array\$1prepend(array, element) | 将元素添加到作为第一个参数传递的数组开头。元素类型应与数组中元素的类型相同。数组前面还会添加 Null 元素。但如果传递的数组为 NULL，则输出为 NULL | 
| array\$1remove(array, element) | 从数组中移除所有等于元素的元素。 | 
| array\$1repeat(element, count) | 返回包含元素计数次数的数组。 | 
| array\$1union(array1, array2) | 返回包含 array1 和 array2 并集元素的数组，且不含重复项。 | 
| arrays\$1overlap(a1, a2) | 如果 a1 中至少包含一个在 a2 中也存在的非 null 元素，则返回 true。如果数组没有公共元素且均为非空，并且其中任何一个都包含 null 元素，则返回 null，否则返回 false。 | 
| arrays\$1zip(a1, a2, ...) | 返回一个合并的结构数组，其中第 N 个结构包含输入数组的所有第 N 个值。 | 
| 展平 () arrayOfArrays | 将数组的数组转换为单个数组。 | 
| get(array, index) | 返回数组中指定索引处（从 0 开始计数）的元素。如果索引超出数组边界，则该函数返回 NULL。 | 
| sequence(start, stop, step) | 生成从起始值到结束值（包含）的元素数组，逐渐递增。返回元素的类型与参数表达式的类型相同。支持的类型包括：字节、短整型、整数、长整型、日期、时间戳。起始和结束表达式必须解析为相同类型。如果起始和结束表达式解析为“日期”或“时间戳”类型，则步骤表达式必须解析为“间隔”、“年-月间隔”或“日-时间间隔”类型，否则应解析为与起始和结束表达式相同的类型。 | 
| shuffle(array) | 返回给定数组的随机排列。 | 
| slice(x, start, length) | 子集数组 x 从索引开始（数组索引从 1 开始，如果起始为负数，则从末尾开始），长度为指定。 | 
| sort\$1array(array[, ascendingOrder]) | 根据数组元素的自然排序规则，将输入数组按升序或降序进行排序。就 double/float 类型而言，NaN 大于任何非 NaN 元素。Null 元素将在返回数组的开头按升序排列，或在返回数组的结尾按降序排列。 | 

**示例**

```
-- array
SELECT array(1, 2, 3);
+--------------+
|array(1, 2, 3)|
+--------------+
|     [1, 2, 3]|
+--------------+
-- array_append
SELECT array_append(array('b', 'd', 'c', 'a'), 'd');
+----------------------------------+
|array_append(array(b, d, c, a), d)|
+----------------------------------+
|                   [b, d, c, a, d]|
+----------------------------------+
SELECT array_append(array(1, 2, 3, null), null);
+----------------------------------------+
|array_append(array(1, 2, 3, NULL), NULL)|
+----------------------------------------+
|                    [1, 2, 3, NULL, N...|
+----------------------------------------+
SELECT array_append(CAST(null as Array<Int>), 2);
+---------------------+
|array_append(NULL, 2)|
+---------------------+
|                 NULL|
+---------------------+
-- array_compact
SELECT array_compact(array(1, 2, 3, null));
+-----------------------------------+
|array_compact(array(1, 2, 3, NULL))|
+-----------------------------------+
|                          [1, 2, 3]|
+-----------------------------------+
SELECT array_compact(array("a", "b", "c"));
+-----------------------------+
|array_compact(array(a, b, c))|
+-----------------------------+
|                    [a, b, c]|
+-----------------------------+
-- array_contains
SELECT array_contains(array(1, 2, 3), 2);
+---------------------------------+
|array_contains(array(1, 2, 3), 2)|
+---------------------------------+
|                             true|
+---------------------------------+
-- array_distinct
SELECT array_distinct(array(1, 2, 3, null, 3));
+---------------------------------------+
|array_distinct(array(1, 2, 3, NULL, 3))|
+---------------------------------------+
|                        [1, 2, 3, NULL]|
+---------------------------------------+
-- array_except
SELECT array_except(array(1, 2, 3), array(1, 3, 5));
+--------------------------------------------+
|array_except(array(1, 2, 3), array(1, 3, 5))|
+--------------------------------------------+
|                                         [2]|
+--------------------------------------------+
-- array_insert
SELECT array_insert(array(1, 2, 3, 4), 5, 5);
+-------------------------------------+
|array_insert(array(1, 2, 3, 4), 5, 5)|
+-------------------------------------+
|                      [1, 2, 3, 4, 5]|
+-------------------------------------+
SELECT array_insert(array(5, 4, 3, 2), -1, 1);
+--------------------------------------+
|array_insert(array(5, 4, 3, 2), -1, 1)|
+--------------------------------------+
|                       [5, 4, 3, 2, 1]|
+--------------------------------------+
SELECT array_insert(array(5, 3, 2, 1), -4, 4);
+--------------------------------------+
|array_insert(array(5, 3, 2, 1), -4, 4)|
+--------------------------------------+
|                       [5, 4, 3, 2, 1]|
+--------------------------------------+
-- array_intersect
SELECT array_intersect(array(1, 2, 3), array(1, 3, 5));
+-----------------------------------------------+
|array_intersect(array(1, 2, 3), array(1, 3, 5))|
+-----------------------------------------------+
|                                         [1, 3]|
+-----------------------------------------------+
-- array_join
SELECT array_join(array('hello', 'world'), ' ');
+----------------------------------+
|array_join(array(hello, world),  )|
+----------------------------------+
|                       hello world|
+----------------------------------+
SELECT array_join(array('hello', null ,'world'), ' ');
+----------------------------------------+
|array_join(array(hello, NULL, world),  )|
+----------------------------------------+
|                             hello world|
+----------------------------------------+
SELECT array_join(array('hello', null ,'world'), ' ', ',');
+-------------------------------------------+
|array_join(array(hello, NULL, world),  , ,)|
+-------------------------------------------+
|                              hello , world|
+-------------------------------------------+
-- array_max
SELECT array_max(array(1, 20, null, 3));
+--------------------------------+
|array_max(array(1, 20, NULL, 3))|
+--------------------------------+
|                              20|
+--------------------------------+
-- array_min
SELECT array_min(array(1, 20, null, 3));
+--------------------------------+
|array_min(array(1, 20, NULL, 3))|
+--------------------------------+
|                               1|
+--------------------------------+
-- array_position
SELECT array_position(array(312, 773, 708, 708), 708);
+----------------------------------------------+
|array_position(array(312, 773, 708, 708), 708)|
+----------------------------------------------+
|                                             3|
+----------------------------------------------+
SELECT array_position(array(312, 773, 708, 708), 414);
+----------------------------------------------+
|array_position(array(312, 773, 708, 708), 414)|
+----------------------------------------------+
|                                             0|
+----------------------------------------------+
-- array_prepend
SELECT array_prepend(array('b', 'd', 'c', 'a'), 'd');
+-----------------------------------+
|array_prepend(array(b, d, c, a), d)|
+-----------------------------------+
|                    [d, b, d, c, a]|
+-----------------------------------+
SELECT array_prepend(array(1, 2, 3, null), null);
+-----------------------------------------+
|array_prepend(array(1, 2, 3, NULL), NULL)|
+-----------------------------------------+
|                     [NULL, 1, 2, 3, N...|
+-----------------------------------------+
SELECT array_prepend(CAST(null as Array<Int>), 2);
+----------------------+
|array_prepend(NULL, 2)|
+----------------------+
|                  NULL|
+----------------------+
-- array_remove
SELECT array_remove(array(1, 2, 3, null, 3), 3);
+----------------------------------------+
|array_remove(array(1, 2, 3, NULL, 3), 3)|
+----------------------------------------+
|                            [1, 2, NULL]|
+----------------------------------------+
-- array_repeat
SELECT array_repeat('123', 2);
+--------------------+
|array_repeat(123, 2)|
+--------------------+
|          [123, 123]|
+--------------------+
-- array_union
SELECT array_union(array(1, 2, 3), array(1, 3, 5));
+-------------------------------------------+
|array_union(array(1, 2, 3), array(1, 3, 5))|
+-------------------------------------------+
|                               [1, 2, 3, 5]|
+-------------------------------------------+
-- arrays_overlap
SELECT arrays_overlap(array(1, 2, 3), array(3, 4, 5));
+----------------------------------------------+
|arrays_overlap(array(1, 2, 3), array(3, 4, 5))|
+----------------------------------------------+
|                                          true|
+----------------------------------------------+
-- arrays_zip
SELECT arrays_zip(array(1, 2, 3), array(2, 3, 4));
+------------------------------------------+
|arrays_zip(array(1, 2, 3), array(2, 3, 4))|
+------------------------------------------+
|                      [{1, 2}, {2, 3}, ...|
+------------------------------------------+
SELECT arrays_zip(array(1, 2), array(2, 3), array(3, 4));
+-------------------------------------------------+
|arrays_zip(array(1, 2), array(2, 3), array(3, 4))|
+-------------------------------------------------+
|                             [{1, 2, 3}, {2, 3...|
+-------------------------------------------------+
-- flatten
SELECT flatten(array(array(1, 2), array(3, 4)));
+----------------------------------------+
|flatten(array(array(1, 2), array(3, 4)))|
+----------------------------------------+
|                            [1, 2, 3, 4]|
+----------------------------------------+
-- get
SELECT get(array(1, 2, 3), 0);
+----------------------+
|get(array(1, 2, 3), 0)|
+----------------------+
|                     1|
+----------------------+
SELECT get(array(1, 2, 3), 3);
+----------------------+
|get(array(1, 2, 3), 3)|
+----------------------+
|                  NULL|
+----------------------+
SELECT get(array(1, 2, 3), -1);
+-----------------------+
|get(array(1, 2, 3), -1)|
+-----------------------+
|                   NULL|
+-----------------------+
-- sequence
SELECT sequence(1, 5);
+---------------+
| sequence(1, 5)|
+---------------+
|[1, 2, 3, 4, 5]|
+---------------+
SELECT sequence(5, 1);
+---------------+
| sequence(5, 1)|
+---------------+
|[5, 4, 3, 2, 1]|
+---------------+
SELECT sequence(to_date('2018-01-01'), to_date('2018-03-01'), interval 1 month);
+----------------------------------------------------------------------+
|sequence(to_date(2018-01-01), to_date(2018-03-01), INTERVAL '1' MONTH)|
+----------------------------------------------------------------------+
|                                                  [2018-01-01, 2018...|
+----------------------------------------------------------------------+
SELECT sequence(to_date('2018-01-01'), to_date('2018-03-01'), interval '0-1' year to month);
+--------------------------------------------------------------------------------+
|sequence(to_date(2018-01-01), to_date(2018-03-01), INTERVAL '0-1' YEAR TO MONTH)|
+--------------------------------------------------------------------------------+
|                                                            [2018-01-01, 2018...|
+--------------------------------------------------------------------------------+
-- shuffle
SELECT shuffle(array(1, 20, 3, 5));
+---------------------------+
|shuffle(array(1, 20, 3, 5))|
+---------------------------+
|              [5, 1, 20, 3]|
+---------------------------+
SELECT shuffle(array(1, 20, null, 3));
+------------------------------+
|shuffle(array(1, 20, NULL, 3))|
+------------------------------+
|              [1, NULL, 20, 3]|
+------------------------------+
-- slice
SELECT slice(array(1, 2, 3, 4), 2, 2);
+------------------------------+
|slice(array(1, 2, 3, 4), 2, 2)|
+------------------------------+
|                        [2, 3]|
+------------------------------+
SELECT slice(array(1, 2, 3, 4), -2, 2);
+-------------------------------+
|slice(array(1, 2, 3, 4), -2, 2)|
+-------------------------------+
|                         [3, 4]|
+-------------------------------+
-- sort_array
SELECT sort_array(array('b', 'd', null, 'c', 'a'), true);
+-----------------------------------------+
|sort_array(array(b, d, NULL, c, a), true)|
+-----------------------------------------+
|                       [NULL, a, b, c, d]|
+-----------------------------------------+
```

#### 窗口函数
<a name="supported-sql-window"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

窗口函数对一组称为窗口的行进行操作，并根据该组行计算每行的返回值。窗口函数适用于处理诸如计算移动平均值、求取累积统计量，或根据当前行相对位置获取行值等任务。

**语法** 

```
window_function [ nulls_option ] OVER ( [ { PARTITION | DISTRIBUTE } BY partition_col_name = partition_col_val ( [ , ... ] ) ] { ORDER | SORT } BY expression [ ASC | DESC ] [ NULLS { FIRST | LAST } ] [ , ... ] [ window_frame ] ) 
```

**参数** 
+ 

  window\$1function 

  排名函数 

  语法：`RANK | DENSE_RANK | PERCENT_RANK | NTILE | ROW_NUMBER `

  分析函数 

  语法：`CUME_DIST | LAG | LEAD | NTH_VALUE | FIRST_VALUE | LAST_VALUE `

  聚合函数 

  语法：`MAX | MIN | COUNT | SUM | AVG | ... `
+ `nulls_option`：指定在评估窗口函数时是否跳过 null 值。RESPECT NULLS 表示不跳过 NULL 值，IGNORE NULLS 表示跳过。如果未指定，则默认为 RESPECT NULLS。

  语法：`{ IGNORE | RESPECT } NULLS `

  注意：`Only LAG` \$1 `LEAD` \$1 `NTH_VALUE` \$1 `FIRST_VALUE` \$1 `LAST_VALUE` 可以与 `IGNORE NULLS` 结合使用。
+ `window_frame`：指定窗口从哪一行开始显示以及在何处结束。

  语法：`{ RANGE | ROWS } { frame_start | BETWEEN frame_start AND frame_end }`

  frame\$1start 和 frame\$1end 的语法如下：

  语法：`UNBOUNDED PRECEDING | offset PRECEDING | CURRENT ROW | offset FOLLOWING | UNBOUNDED FOLLOWING `

  偏移量：指定相对于当前行位置的偏移量。

  **注意**，如果省略 frame\$1end，则默认为 CURRENT ROW。

**示例**

```
CREATE TABLE employees (name STRING, dept STRING, salary INT, age INT);
INSERT INTO employees VALUES ("Lisa", "Sales", 10000, 35);
INSERT INTO employees VALUES ("Evan", "Sales", 32000, 38);
INSERT INTO employees VALUES ("Fred", "Engineering", 21000, 28);
INSERT INTO employees VALUES ("Alex", "Sales", 30000, 33);
INSERT INTO employees VALUES ("Tom", "Engineering", 23000, 33);
INSERT INTO employees VALUES ("Jane", "Marketing", 29000, 28);
INSERT INTO employees VALUES ("Jeff", "Marketing", 35000, 38);
INSERT INTO employees VALUES ("Paul", "Engineering", 29000, 23);
INSERT INTO employees VALUES ("Chloe", "Engineering", 23000, 25);
SELECT * FROM employees;
+-----+-----------+------+-----+
| name|       dept|salary|  age|
+-----+-----------+------+-----+
|Chloe|Engineering| 23000|   25|
| Fred|Engineering| 21000|   28|
| Paul|Engineering| 29000|   23|
|Helen|  Marketing| 29000|   40|
|  Tom|Engineering| 23000|   33|
| Jane|  Marketing| 29000|   28|
| Jeff|  Marketing| 35000|   38|
| Evan|      Sales| 32000|   38|
| Lisa|      Sales| 10000|   35|
| Alex|      Sales| 30000|   33|
+-----+-----------+------+-----+
SELECT name, dept, salary, RANK() OVER (PARTITION BY dept ORDER BY salary) AS rank FROM employees;
+-----+-----------+------+----+
| name|       dept|salary|rank|
+-----+-----------+------+----+
| Lisa|      Sales| 10000|   1|
| Alex|      Sales| 30000|   2|
| Evan|      Sales| 32000|   3|
| Fred|Engineering| 21000|   1|
|  Tom|Engineering| 23000|   2|
|Chloe|Engineering| 23000|   2|
| Paul|Engineering| 29000|   4|
|Helen|  Marketing| 29000|   1|
| Jane|  Marketing| 29000|   1|
| Jeff|  Marketing| 35000|   3|
+-----+-----------+------+----+
SELECT name, dept, salary, DENSE_RANK() OVER (PARTITION BY dept ORDER BY salary ROWS BETWEEN
UNBOUNDED PRECEDING AND CURRENT ROW) AS dense_rank FROM employees;
+-----+-----------+------+----------+
| name|       dept|salary|dense_rank|
+-----+-----------+------+----------+
| Lisa|      Sales| 10000|         1|
| Alex|      Sales| 30000|         2|
| Evan|      Sales| 32000|         3|
| Fred|Engineering| 21000|         1|
|  Tom|Engineering| 23000|         2|
|Chloe|Engineering| 23000|         2|
| Paul|Engineering| 29000|         3|
|Helen|  Marketing| 29000|         1|
| Jane|  Marketing| 29000|         1|
| Jeff|  Marketing| 35000|         2|
+-----+-----------+------+----------+
SELECT name, dept, age, CUME_DIST() OVER (PARTITION BY dept ORDER BY age
RANGE BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW) AS cume_dist FROM employees;
+-----+-----------+------+------------------+
| name|       dept|age   |         cume_dist|
+-----+-----------+------+------------------+
| Alex|      Sales|    33|0.3333333333333333|
| Lisa|      Sales|    35|0.6666666666666666|
| Evan|      Sales|    38|               1.0|
| Paul|Engineering|    23|              0.25|
|Chloe|Engineering|    25|              0.75|
| Fred|Engineering|    28|              0.25|
|  Tom|Engineering|    33|               1.0|
| Jane|  Marketing|    28|0.3333333333333333|
| Jeff|  Marketing|    38|0.6666666666666666|
|Helen|  Marketing|    40|               1.0|
+-----+-----------+------+------------------+
SELECT name, dept, salary, MIN(salary) OVER (PARTITION BY dept ORDER BY salary) AS min
FROM employees;
+-----+-----------+------+-----+
| name|       dept|salary|  min|
+-----+-----------+------+-----+
| Lisa|      Sales| 10000|10000|
| Alex|      Sales| 30000|10000|
| Evan|      Sales| 32000|10000|
|Helen|  Marketing| 29000|29000|
| Jane|  Marketing| 29000|29000|
| Jeff|  Marketing| 35000|29000|
| Fred|Engineering| 21000|21000|
|  Tom|Engineering| 23000|21000|
|Chloe|Engineering| 23000|21000|
| Paul|Engineering| 29000|21000|
+-----+-----------+------+-----+
SELECT name, salary,
LAG(salary) OVER (PARTITION BY dept ORDER BY salary) AS lag,
LEAD(salary, 1, 0) OVER (PARTITION BY dept ORDER BY salary) AS lead
FROM employees;
+-----+-----------+------+-----+-----+
| name|       dept|salary|  lag| lead|
+-----+-----------+------+-----+-----+
| Lisa|      Sales| 10000|NULL |30000|
| Alex|      Sales| 30000|10000|32000|
| Evan|      Sales| 32000|30000|    0|
| Fred|Engineering| 21000| NULL|23000|
|Chloe|Engineering| 23000|21000|23000|
|  Tom|Engineering| 23000|23000|29000|
| Paul|Engineering| 29000|23000|    0|
|Helen|  Marketing| 29000| NULL|29000|
| Jane|  Marketing| 29000|29000|35000|
| Jeff|  Marketing| 35000|29000|    0|
+-----+-----------+------+-----+-----+
SELECT id, v,
LEAD(v, 0) IGNORE NULLS OVER w lead,
LAG(v, 0) IGNORE NULLS OVER w lag,
NTH_VALUE(v, 2) IGNORE NULLS OVER w nth_value,
FIRST_VALUE(v) IGNORE NULLS OVER w first_value,
LAST_VALUE(v) IGNORE NULLS OVER w last_value
FROM test_ignore_null
WINDOW w AS (ORDER BY id)
ORDER BY id;
+--+----+----+----+---------+-----------+----------+
|id|   v|lead| lag|nth_value|first_value|last_value|
+--+----+----+----+---------+-----------+----------+
| 0|NULL|NULL|NULL|     NULL|       NULL|      NULL|
| 1|   x|   x|   x|     NULL|          x|         x|
| 2|NULL|NULL|NULL|     NULL|          x|         x|
| 3|NULL|NULL|NULL|     NULL|          x|         x|
| 4|   y|   y|   y|        y|          x|         y|
| 5|NULL|NULL|NULL|        y|          x|         y|
| 6|   z|   z|   z|        y|          x|         z|
| 7|   v|   v|   v|        y|          x|         v|
| 8|NULL|NULL|NULL|        y|          x|         v|
+--+----+----+----+---------+-----------+----------+
```

#### 转换函数
<a name="supported-sql-conversion"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。


****  

| 函数 | 说明 | 
| --- | --- | 
| bigint(expr) | 将值 `expr` 转换为目标数据类型 `bigint`。 | 
| binary(expr) | 将值 `expr` 转换为目标数据类型 `binary`。 | 
| boolean(expr) | 将值 `expr` 转换为目标数据类型 `boolean`。 | 
| cast(expr AS type) | 将值 `expr` 转换为目标数据类型 `type`。 | 
| date(expr) | 将值 `expr` 转换为目标数据类型 `date`。 | 
| decimal(expr) | 将值 `expr` 转换为目标数据类型 `decimal`。 | 
| double(expr) | 将值 `expr` 转换为目标数据类型 `double`。 | 
| float(expr) | 将值 `expr` 转换为目标数据类型 `float`。 | 
| int(expr) | 将值 `expr` 转换为目标数据类型 `int`。 | 
| smallint(expr) | 将值 `expr` 转换为目标数据类型 `smallint`。 | 
| string(expr) | 将值 `expr` 转换为目标数据类型 `string`。 | 
| timestamp(expr) | 将值 `expr` 转换为目标数据类型 `timestamp`。 | 
| tinyint(expr) | 将值 `expr` 转换为目标数据类型 `tinyint`。 | 

**示例**

```
-- cast
SELECT cast(field as int);
+---------------+
|CAST(field AS INT)|
+---------------+
|             10|
+---------------+
```

#### 谓词函数
<a name="supported-sql-predicate"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。


****  

| 函数 | 说明 | 
| --- | --- | 
| \$1 expr | 逻辑非。 | 
| expr1 < expr2 | 如果 `expr1` 小于 `expr2`，则返回 true。 | 
| expr1 <= expr2 | 如果 `expr1` 小于等于 `expr2`，则返回 true。 | 
| expr1 <=> expr2 | 对于非 null 操作数，返回与 EQUAL(=) 运算符相同的结果，但如果两者都为 null，则返回 true；如果其中一个为 null，则返回 false。 | 
| expr1 = expr2 | 如果 `expr1` 等于 `expr2`，则返回 true，否则返回 false。 | 
| expr1 == expr2 | 如果 `expr1` 等于 `expr2`，则返回 true，否则返回 false。 | 
| expr1 > expr2 | 如果 `expr1` 大于 `expr2`，则返回 true。 | 
| expr1 >= expr2 | 如果 `expr1` 大于等于 `expr2`，则返回 true。 | 
| expr1 and expr2 | 逻辑 AND。 | 
| str ilike pattern[ ESCAPE escape] | 如果字符串 str 与带 `escape` 的 `pattern` 匹配（不区分大小写），则返回 true；如果任何参数为 null，则返回 null；否则返回 false。 | 
| expr1 in(expr2, expr3, ...) | 如果 `expr` 等于任何 valN，则返回 true。 | 
| isnan(expr) | 如果 `expr` 为 NaN，则返回 true，否则返回 false。 | 
| isnotnull(expr) | 如果 `expr` 不为 null，则返回 true，否则返回 false。 | 
| isnull(expr) | 如果 `expr` 为 null，则返回 true，否则返回 false。 | 
| str like pattern[ ESCAPE escape] | 如果字符串 str 与带 `escape` 的 `pattern` 匹配，则返回 true；如果任何参数为 null，则返回 null；否则返回 false。 | 
| not expr | 逻辑非。 | 
| expr1 or expr2 | 逻辑 OR。 | 
| regexp(str, regexp) | 如果 `str` 与 `regexp` 匹配，则返回 true，否则返回 false。 | 
| regexp\$1like(str, regexp) | 如果 `str` 与 `regexp` 匹配，则返回 true，否则返回 false。 | 
| rlike(str, regexp) | 如果 `str` 与 `regexp` 匹配，则返回 true，否则返回 false。 | 

**示例**

```
-- !
SELECT ! true;
+----------+
|(NOT true)|
+----------+
|     false|
+----------+
SELECT ! false;
+-----------+
|(NOT false)|
+-----------+
|       true|
+-----------+
SELECT ! NULL;
+----------+
|(NOT NULL)|
+----------+
|      NULL|
+----------+
-- <
SELECT to_date('2009-07-30 04:17:52') < to_date('2009-07-30 04:17:52');
+-------------------------------------------------------------+
|(to_date(2009-07-30 04:17:52) < to_date(2009-07-30 04:17:52))|
+-------------------------------------------------------------+
|                                                        false|
+-------------------------------------------------------------+
SELECT to_date('2009-07-30 04:17:52') < to_date('2009-08-01 04:17:52');
+-------------------------------------------------------------+
|(to_date(2009-07-30 04:17:52) < to_date(2009-08-01 04:17:52))|
+-------------------------------------------------------------+
|                                                         true|
+-------------------------------------------------------------+
SELECT 1 < NULL;
+----------+
|(1 < NULL)|
+----------+
|      NULL|
+----------+
-- <=
SELECT 2 <= 2;
+--------+
|(2 <= 2)|
+--------+
|    true|
+--------+
SELECT 1.0 <= '1';
+----------+
|(1.0 <= 1)|
+----------+
|      true|
+----------+
SELECT to_date('2009-07-30 04:17:52') <= to_date('2009-07-30 04:17:52');
+--------------------------------------------------------------+
|(to_date(2009-07-30 04:17:52) <= to_date(2009-07-30 04:17:52))|
+--------------------------------------------------------------+
|                                                          true|
+--------------------------------------------------------------+
SELECT to_date('2009-07-30 04:17:52') <= to_date('2009-08-01 04:17:52');
+--------------------------------------------------------------+
|(to_date(2009-07-30 04:17:52) <= to_date(2009-08-01 04:17:52))|
+--------------------------------------------------------------+
|                                                          true|
+--------------------------------------------------------------+
SELECT 1 <= NULL;
+-----------+
|(1 <= NULL)|
+-----------+
|       NULL|
+-----------+
-- <=>
SELECT 2 <=> 2;
+---------+
|(2 <=> 2)|
+---------+
|     true|
+---------+
SELECT 1 <=> '1';
+---------+
|(1 <=> 1)|
+---------+
|     true|
+---------+
SELECT true <=> NULL;
+---------------+
|(true <=> NULL)|
+---------------+
|          false|
+---------------+
SELECT NULL <=> NULL;
+---------------+
|(NULL <=> NULL)|
+---------------+
|           true|
+---------------+
-- =
SELECT 2 = 2;
+-------+
|(2 = 2)|
+-------+
|   true|
+-------+
SELECT 1 = '1';
+-------+
|(1 = 1)|
+-------+
|   true|
+-------+
SELECT true = NULL;
+-------------+
|(true = NULL)|
+-------------+
|         NULL|
+-------------+
SELECT NULL = NULL;
+-------------+
|(NULL = NULL)|
+-------------+
|         NULL|
+-------------+
-- ==
SELECT 2 == 2;
+-------+
|(2 = 2)|
+-------+
|   true|
+-------+
SELECT 1 == '1';
+-------+
|(1 = 1)|
+-------+
|   true|
+-------+
SELECT true == NULL;
+-------------+
|(true = NULL)|
+-------------+
|         NULL|
+-------------+
SELECT NULL == NULL;
+-------------+
|(NULL = NULL)|
+-------------+
|         NULL|
+-------------+
-- >
SELECT 2 > 1;
+-------+
|(2 > 1)|
+-------+
|   true|
+-------+
SELECT 2 > 1.1;
+-------+
|(2 > 1)|
+-------+
|   true|
+-------+
SELECT to_date('2009-07-30 04:17:52') > to_date('2009-07-30 04:17:52');
+-------------------------------------------------------------+
|(to_date(2009-07-30 04:17:52) > to_date(2009-07-30 04:17:52))|
+-------------------------------------------------------------+
|                                                        false|
+-------------------------------------------------------------+
SELECT to_date('2009-07-30 04:17:52') > to_date('2009-08-01 04:17:52');
+-------------------------------------------------------------+
|(to_date(2009-07-30 04:17:52) > to_date(2009-08-01 04:17:52))|
+-------------------------------------------------------------+
|                                                        false|
+-------------------------------------------------------------+
SELECT 1 > NULL;
+----------+
|(1 > NULL)|
+----------+
|      NULL|
+----------+
-- >=
SELECT 2 >= 1;
+--------+
|(2 >= 1)|
+--------+
|    true|
+--------+
SELECT 2.0 >= '2.1';
+------------+
|(2.0 >= 2.1)|
+------------+
|       false|
+------------+
SELECT to_date('2009-07-30 04:17:52') >= to_date('2009-07-30 04:17:52');
+--------------------------------------------------------------+
|(to_date(2009-07-30 04:17:52) >= to_date(2009-07-30 04:17:52))|
+--------------------------------------------------------------+
|                                                          true|
+--------------------------------------------------------------+
SELECT to_date('2009-07-30 04:17:52') >= to_date('2009-08-01 04:17:52');
+--------------------------------------------------------------+
|(to_date(2009-07-30 04:17:52) >= to_date(2009-08-01 04:17:52))|
+--------------------------------------------------------------+
|                                                         false|
+--------------------------------------------------------------+
SELECT 1 >= NULL;
+-----------+
|(1 >= NULL)|
+-----------+
|       NULL|
+-----------+
-- and
SELECT true and true;
+---------------+
|(true AND true)|
+---------------+
|           true|
+---------------+
SELECT true and false;
+----------------+
|(true AND false)|
+----------------+
|           false|
+----------------+
SELECT true and NULL;
+---------------+
|(true AND NULL)|
+---------------+
|           NULL|
+---------------+
SELECT false and NULL;
+----------------+
|(false AND NULL)|
+----------------+
|           false|
+----------------+
-- ilike
SELECT ilike('Wagon', '_Agon');
+-------------------+
|ilike(Wagon, _Agon)|
+-------------------+
|               true|
+-------------------+
SELECT '%SystemDrive%\Users\John' ilike '\%SystemDrive\%\\users%';
+--------------------------------------------------------+
|ilike(%SystemDrive%\Users\John, \%SystemDrive\%\\users%)|
+--------------------------------------------------------+
|                                                    true|
+--------------------------------------------------------+
SELECT '%SystemDrive%\\USERS\\John' ilike '\%SystemDrive\%\\\\Users%';
+--------------------------------------------------------+
|ilike(%SystemDrive%\USERS\John, \%SystemDrive\%\\Users%)|
+--------------------------------------------------------+
|                                                    true|
+--------------------------------------------------------+
SELECT '%SystemDrive%/Users/John' ilike '/%SYSTEMDrive/%//Users%' ESCAPE '/';
+--------------------------------------------------------+
|ilike(%SystemDrive%/Users/John, /%SYSTEMDrive/%//Users%)|
+--------------------------------------------------------+
|                                                    true|
+--------------------------------------------------------+
-- in
SELECT 1 in(1, 2, 3);
+----------------+
|(1 IN (1, 2, 3))|
+----------------+
|            true|
+----------------+
SELECT 1 in(2, 3, 4);
+----------------+
|(1 IN (2, 3, 4))|
+----------------+
|           false|
+----------------+
SELECT named_struct('a', 1, 'b', 2) in(named_struct('a', 1, 'b', 1), named_struct('a', 1, 'b', 3));
+----------------------------------------------------------------------------------+
|(named_struct(a, 1, b, 2) IN (named_struct(a, 1, b, 1), named_struct(a, 1, b, 3)))|
+----------------------------------------------------------------------------------+
|                                                                             false|
+----------------------------------------------------------------------------------+
SELECT named_struct('a', 1, 'b', 2) in(named_struct('a', 1, 'b', 2), named_struct('a', 1, 'b', 3));
+----------------------------------------------------------------------------------+
|(named_struct(a, 1, b, 2) IN (named_struct(a, 1, b, 2), named_struct(a, 1, b, 3)))|
+----------------------------------------------------------------------------------+
|                                                                              true|
+----------------------------------------------------------------------------------+
-- isnan
SELECT isnan(cast('NaN' as double));
+--------------------------+
|isnan(CAST(NaN AS DOUBLE))|
+--------------------------+
|                      true|
+--------------------------+
-- isnotnull
SELECT isnotnull(1);
+---------------+
|(1 IS NOT NULL)|
+---------------+
|           true|
+---------------+
-- isnull
SELECT isnull(1);
+-----------+
|(1 IS NULL)|
+-----------+
|      false|
+-----------+
-- like
SELECT like('Wagon', '_Agon');
+----------------+
|Wagon LIKE _Agon|
+----------------+
|            true|
+----------------+
-- not
SELECT not true;
+----------+
|(NOT true)|
+----------+
|     false|
+----------+
SELECT not false;
+-----------+
|(NOT false)|
+-----------+
|       true|
+-----------+
SELECT not NULL;
+----------+
|(NOT NULL)|
+----------+
|      NULL|
+----------+
-- or
SELECT true or false;
+---------------+
|(true OR false)|
+---------------+
|           true|
+---------------+
SELECT false or false;
+----------------+
|(false OR false)|
+----------------+
|           false|
+----------------+
SELECT true or NULL;
+--------------+
|(true OR NULL)|
+--------------+
|          true|
+--------------+
SELECT false or NULL;
+---------------+
|(false OR NULL)|
+---------------+
|           NULL|
+---------------+
```

#### 映射函数
<a name="supported-sql-map"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。


****  

| 函数 | 说明 | 
| --- | --- | 
| element\$1at(array, index) | 返回数组中指定索引处（从 1 开始计数）的元素。 | 
| element\$1at(map, key) | 返回给定键的值。如果键不在映射中，则该函数返回 NULL。 | 
| map(key0, value0, key1, value1, ...) | 用给定的配 key/value 对创建地图。 | 
| map\$1concat(map, ...) | 返回所有给定映射的并集 | 
| map\$1contains\$1key(map, key) | 如果映射包含键，则返回 true。 | 
| map\$1entries(map) | 返回给定映射中所有条目的无序数组。 | 
| map\$1from\$1arrays(keys, values) | 使用一对给定 key/value 数组创建地图。键中所有元素均不应为 null | 
| map\$1from\$1entries () arrayOfEntries | 返回根据给定条目数组创建的映射。 | 
| map\$1keys(map) | 返回包含映射的键的无序数组。 | 
| map\$1values(map) | 返回包含映射的值的无序数组。 | 
| str\$1to\$1map（文本 [，pairDelim [，]]） keyValueDelim | 将文本按分隔符拆分为键值对后创建映射。“pairDelim` 的默认分隔符是 '、' 和 ':' 代表 `。keyValueDelim`pairDelim`和``都被视为正则表达式。keyValueDelim | 
| try\$1element\$1at(array, index) | 返回数组中指定索引处（从 1 开始计数）的元素。如果索引为 0，系统将抛出错误。如果索引 < 0，则从最后一个元素开始访问元素直至第一个元素。如果索引超过数组的长度，则函数始终返回 NULL。 | 
| try\$1element\$1at(map, key) | 返回给定键的值。如果键不在映射中，则该函数始终返回 NULL。 | 

**示例**

```
-- element_at
SELECT element_at(array(1, 2, 3), 2);
+-----------------------------+
|element_at(array(1, 2, 3), 2)|
+-----------------------------+
|                            2|
+-----------------------------+
SELECT element_at(map(1, 'a', 2, 'b'), 2);
+------------------------------+
|element_at(map(1, a, 2, b), 2)|
+------------------------------+
|                             b|
+------------------------------+
-- map
SELECT map(1.0, '2', 3.0, '4');
+--------------------+
| map(1.0, 2, 3.0, 4)|
+--------------------+
|{1.0 -> 2, 3.0 -> 4}|
+--------------------+
-- map_concat
SELECT map_concat(map(1, 'a', 2, 'b'), map(3, 'c'));
+--------------------------------------+
|map_concat(map(1, a, 2, b), map(3, c))|
+--------------------------------------+
|                  {1 -> a, 2 -> b, ...|
+--------------------------------------+
-- map_contains_key
SELECT map_contains_key(map(1, 'a', 2, 'b'), 1);
+------------------------------------+
|map_contains_key(map(1, a, 2, b), 1)|
+------------------------------------+
|                                true|
+------------------------------------+
SELECT map_contains_key(map(1, 'a', 2, 'b'), 3);
+------------------------------------+
|map_contains_key(map(1, a, 2, b), 3)|
+------------------------------------+
|                               false|
+------------------------------------+
-- map_entries
SELECT map_entries(map(1, 'a', 2, 'b'));
+----------------------------+
|map_entries(map(1, a, 2, b))|
+----------------------------+
|            [{1, a}, {2, b}]|
+----------------------------+
-- map_from_arrays
SELECT map_from_arrays(array(1.0, 3.0), array('2', '4'));
+---------------------------------------------+
|map_from_arrays(array(1.0, 3.0), array(2, 4))|
+---------------------------------------------+
|                         {1.0 -> 2, 3.0 -> 4}|
+---------------------------------------------+
-- map_from_entries
SELECT map_from_entries(array(struct(1, 'a'), struct(2, 'b')));
+---------------------------------------------------+
|map_from_entries(array(struct(1, a), struct(2, b)))|
+---------------------------------------------------+
|                                   {1 -> a, 2 -> b}|
+---------------------------------------------------+
-- map_keys
SELECT map_keys(map(1, 'a', 2, 'b'));
+-------------------------+
|map_keys(map(1, a, 2, b))|
+-------------------------+
|                   [1, 2]|
+-------------------------+
-- map_values
SELECT map_values(map(1, 'a', 2, 'b'));
+---------------------------+
|map_values(map(1, a, 2, b))|
+---------------------------+
|                     [a, b]|
+---------------------------+
-- str_to_map
SELECT str_to_map('a:1,b:2,c:3', ',', ':');
+-----------------------------+
|str_to_map(a:1,b:2,c:3, ,, :)|
+-----------------------------+
|         {a -> 1, b -> 2, ...|
+-----------------------------+
SELECT str_to_map('a');
+-------------------+
|str_to_map(a, ,, :)|
+-------------------+
|        {a -> NULL}|
+-------------------+
-- try_element_at
SELECT try_element_at(array(1, 2, 3), 2);
+---------------------------------+
|try_element_at(array(1, 2, 3), 2)|
+---------------------------------+
|                                2|
+---------------------------------+
SELECT try_element_at(map(1, 'a', 2, 'b'), 2);
+----------------------------------+
|try_element_at(map(1, a, 2, b), 2)|
+----------------------------------+
|                                 b|
+----------------------------------+
```

#### 数学函数
<a name="supported-sql-math"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。


****  

| 函数 | 说明 | 
| --- | --- | 
| expr1 % expr2 | 返回 `expr1`/`expr2` 运算后的余数。 | 
| expr1 \$1 expr2 | 返回 `expr1`\$1`expr2`。 | 
| expr1 \$1 expr2 | 返回 `expr1`\$1`expr2`。 | 
| expr1 - expr2 | 返回 `expr1`-`expr2`。 | 
| expr1 / expr2 | 返回 `expr1`/`expr2`。总是使用浮点除法。 | 
| abs(expr) | 返回数值或区间值的绝对值。 | 
| acos(expr) | 返回 `expr` 的反余弦值，其计算方式与 `java.lang.Math.acos` 一致。 | 
| acosh(expr) | 返回 `expr` 的反双曲余弦值。 | 
| asin(expr) | 返回 `expr` 的反正弦值，其计算方式与 `java.lang.Math.asin` 一致。 | 
| asinh(expr) | 返回 `expr` 的反双曲正弦值。 | 
| atan(expr) | 返回 `expr` 的反正切值，其计算方式与 `java.lang.Math.atan` 一致 | 
| atan2(exprY, exprX) | 返回平面正 x 轴与坐标点 (`exprX`, `exprY`) 之间夹角的弧度值，其计算方式与 `java.lang.Math.atan2` 一致。 | 
| atanh(expr) | 返回 `expr` 的反双曲正切值。 | 
| bin(expr) | 返回长整型值 `expr` 的二进制字符串表示形式。 | 
| bround(expr, d) | 返回按 `d` 位小数精度四舍五入的 `expr`，采用 HALF\$1EVEN 舍入规则。 | 
| cbrt(expr) | 返回 `expr` 的立方根。 | 
| ceil(expr[, scale]) | 返回四舍五入后不小于 `expr` 的最小数值。可选的 `scale` 参数可用于控制舍入行为。 | 
| ceiling(expr[, scale]) | 返回四舍五入后不小于 `expr` 的最小数值。可选的 `scale` 参数可用于控制舍入行为。 | 
| conv(num, from\$1base, to\$1base) | 将 `num` 从 `from\$1base` 转换为 `to\$1base`。 | 
| cos(expr) | 返回 `expr` 的余弦值，其计算方式与 `java.lang.Math.cos` 一致。 | 
| cosh(expr) | 返回 `expr` 的双曲余弦值，其计算方式与 `java.lang.Math.cosh` 一致。 | 
| cot(expr) | 返回 `expr` 的余切值，其计算方式与 `1/java.lang.Math.tan` 一致。 | 
| csc(expr) | 返回 `expr` 的余割值，其计算方式与 `1/java.lang.Math.sin` 一致。 | 
| degrees(expr) | 将弧度转换为度。 | 
| expr1 div expr2 | `expr1` 除以 `expr2`。如果操作数为 NULL 或 `expr2` 为 0，则返回 NULL。结果将强制转换为长整型。 | 
| e() | 返回欧拉常数 e。 | 
| exp(expr) | 返回 e 的 `expr` 次幂。 | 
| expm1(expr)：返回 exp(`expr`) | 1 | 
| factorial(expr) | 返回 `expr` 的阶乘。`expr` 的取值范围为 [0..20]。否则为 null。 | 
| floor(expr[, scale]) | 返回向下取整后不大于 `expr` 的最大数值。可选的 `scale` 参数可用于控制舍入行为。 | 
| greatest(expr, ...) | 返回所有参数中的最大值，跳过 null 值。 | 
| hex(expr) | 将 `expr` 转换为十六进制。 | 
| hypot(expr1, expr2) | 返回 sqrt(`expr1`\$1\$12 \$1 `expr2`\$1\$12)。 | 
| least(expr, ...) | 返回所有参数中的最小值，跳过 null 值。 | 
| ln(expr) | 返回 `expr` 的自然对数（以 e 为底）。 | 
| log(base, expr) | 返回以 `base` 为底 `expr` 的对数。 | 
| log10(expr) | 返回以 10 为底 `expr` 的对数。 | 
| log1p(expr) | 返回 log(1 \$1 `expr`)。 | 
| log2(expr) | 返回以 2 为底 `expr` 的对数。 | 
| expr1 mod expr2 | 返回 `expr1`/`expr2` 运算后的余数。 | 
| negative(expr) | 返回 `expr` 的取反值。 | 
| pi() | 返回 pi。 | 
| pmod(expr1, expr2) | 返回 `expr1` 除以 `expr2` 的余数（取整数部分）。 | 
| positive(expr) | 返回 `expr` 的值。 | 
| pow(expr1, expr2) | 将 `expr1` 乘方为 `expr2` 次。 | 
| power(expr1, expr2) | 将 `expr1` 乘方为 `expr2` 次。 | 
| radians(expr) | 将度转换为弧度。 | 
| rand([seed]) | 返回随机值，该值在 [0, 1) 区间内呈独立同分布（i.i.d.）的均匀分布。 | 
| randn([seed]) | 返回随机值，该值从标准正态分布中抽取，具有独立同分布（i.i.d.）特性。 | 
| random([seed]) | 返回随机值，该值在 [0, 1) 区间内呈独立同分布（i.i.d.）的均匀分布。 | 
| rint(expr) | 返回与参数值最接近且等于数学整数的双精度值。 | 
| round(expr, d) | 返回按 `d` 位小数精度四舍五入的 `expr`，采用 HALF\$1UP 舍入规则。 | 
| sec(expr) | 返回 `expr` 的正割值，其计算方式与 `1/java.lang.Math.cos` 一致。 | 
| shiftleft(base, expr) | 按位左移。 | 
| sign(expr) | 返回 -1.0、0.0 或 1.0，取决于 `expr` 是负数、0 还是正数。 | 
| signum(expr) | 返回 -1.0、0.0 或 1.0，取决于 `expr` 是负数、0 还是正数。 | 
| sin(expr) | 返回 `expr` 的正弦值，其计算方式与 `java.lang.Math.sin` 一致。 | 
| sinh(expr) | 返回 `expr` 的双曲正弦值，其计算方式与 `java.lang.Math.sinh` 一致。 | 
| sqrt(expr) | 返回 `expr` 的平方根。 | 
| tan(expr) | 返回 `expr` 的正切值，其计算方式与 `java.lang.Math.tan` 一致。 | 
| tanh(expr) | 返回 `expr` 的双曲正切值，其计算方式与 `java.lang.Math.tanh` 一致。 | 
| try\$1add(expr1, expr2) | 返回 `expr1` 和 `expr2` 的和，当发生溢出时结果为 null。可接受的输入类型与 `\$1` 运算符相同。 | 
| try\$1divide(dividend, divisor) | 返回 `dividend`/`divisor`。总是使用浮点除法。如果 `expr2` 为 0，则其结果始终为 null。`dividend` 必须是数值或区间类型。。`divisor`必须是数值。 | 
| try\$1multiply(expr1, expr2) | 返回 `expr1`\$1`expr2`，当发生溢出时结果为 null。可接受的输入类型与 `\$1` 运算符相同。 | 
| try\$1subtract(expr1, expr2) | 返回 `expr1`-`expr2`，当发生溢出时结果为 null。可接受的输入类型与 `-` 运算符相同。 | 
| unhex(expr) | 将十六进制 `expr` 转换为二进制。 | 
| width\$1bucket(value, min\$1value, max\$1value, num\$1bucket) | 返回带有 `num\$1buckets` 存储桶的等宽直方图中，`value` 为存储桶编号，范围为 `min\$1value` 到 `max\$1value`。 | 

**示例**

```
-- %
SELECT 2 % 1.8;
+---------+
|(2 % 1.8)|
+---------+
|      0.2|
+---------+
SELECT MOD(2, 1.8);
+-----------+
|mod(2, 1.8)|
+-----------+
|        0.2|
+-----------+
-- *
SELECT 2 * 3;
+-------+
|(2 * 3)|
+-------+
|      6|
+-------+
-- +
SELECT 1 + 2;
+-------+
|(1 + 2)|
+-------+
|      3|
+-------+
-- -
SELECT 2 - 1;
+-------+
|(2 - 1)|
+-------+
|      1|
+-------+
-- /
SELECT 3 / 2;
+-------+
|(3 / 2)|
+-------+
|    1.5|
+-------+
SELECT 2L / 2L;
+-------+
|(2 / 2)|
+-------+
|    1.0|
+-------+
-- abs
SELECT abs(-1);
+-------+
|abs(-1)|
+-------+
|      1|
+-------+
SELECT abs(INTERVAL -'1-1' YEAR TO MONTH);
+----------------------------------+
|abs(INTERVAL '-1-1' YEAR TO MONTH)|
+----------------------------------+
|              INTERVAL '1-1' YE...|
+----------------------------------+
-- acos
SELECT acos(1);
+-------+
|ACOS(1)|
+-------+
|    0.0|
+-------+
SELECT acos(2);
+-------+
|ACOS(2)|
+-------+
|    NaN|
+-------+
-- acosh
SELECT acosh(1);
+--------+
|ACOSH(1)|
+--------+
|     0.0|
+--------+
SELECT acosh(0);
+--------+
|ACOSH(0)|
+--------+
|     NaN|
+--------+
-- asin
SELECT asin(0);
+-------+
|ASIN(0)|
+-------+
|    0.0|
+-------+
SELECT asin(2);
+-------+
|ASIN(2)|
+-------+
|    NaN|
+-------+
-- asinh
SELECT asinh(0);
+--------+
|ASINH(0)|
+--------+
|     0.0|
+--------+
-- atan
SELECT atan(0);
+-------+
|ATAN(0)|
+-------+
|    0.0|
+-------+
-- atan2
SELECT atan2(0, 0);
+-----------+
|ATAN2(0, 0)|
+-----------+
|        0.0|
+-----------+
-- atanh
SELECT atanh(0);
+--------+
|ATANH(0)|
+--------+
|     0.0|
+--------+
SELECT atanh(2);
+--------+
|ATANH(2)|
+--------+
|     NaN|
+--------+
-- bin
SELECT bin(13);
+-------+
|bin(13)|
+-------+
|   1101|
+-------+
SELECT bin(-13);
+--------------------+
|            bin(-13)|
+--------------------+
|11111111111111111...|
+--------------------+
SELECT bin(13.3);
+---------+
|bin(13.3)|
+---------+
|     1101|
+---------+
-- bround
SELECT bround(2.5, 0);
+--------------+
|bround(2.5, 0)|
+--------------+
|             2|
+--------------+
SELECT bround(25, -1);
+--------------+
|bround(25, -1)|
+--------------+
|            20|
+--------------+
-- cbrt
SELECT cbrt(27.0);
+----------+
|CBRT(27.0)|
+----------+
|       3.0|
+----------+
-- ceil
SELECT ceil(-0.1);
+----------+
|CEIL(-0.1)|
+----------+
|         0|
+----------+
SELECT ceil(5);
+-------+
|CEIL(5)|
+-------+
|      5|
+-------+
SELECT ceil(3.1411, 3);
+---------------+
|ceil(3.1411, 3)|
+---------------+
|          3.142|
+---------------+
SELECT ceil(3.1411, -3);
+----------------+
|ceil(3.1411, -3)|
+----------------+
|            1000|
+----------------+
-- ceiling
SELECT ceiling(-0.1);
+-------------+
|ceiling(-0.1)|
+-------------+
|            0|
+-------------+
SELECT ceiling(5);
+----------+
|ceiling(5)|
+----------+
|         5|
+----------+
SELECT ceiling(3.1411, 3);
+------------------+
|ceiling(3.1411, 3)|
+------------------+
|             3.142|
+------------------+
SELECT ceiling(3.1411, -3);
+-------------------+
|ceiling(3.1411, -3)|
+-------------------+
|               1000|
+-------------------+
-- conv
SELECT conv('100', 2, 10);
+----------------+
|conv(100, 2, 10)|
+----------------+
|               4|
+----------------+
SELECT conv(-10, 16, -10);
+------------------+
|conv(-10, 16, -10)|
+------------------+
|               -16|
+------------------+
-- cos
SELECT cos(0);
+------+
|COS(0)|
+------+
|   1.0|
+------+
-- cosh
SELECT cosh(0);
+-------+
|COSH(0)|
+-------+
|    1.0|
+-------+
-- cot
SELECT cot(1);
+------------------+
|            COT(1)|
+------------------+
|0.6420926159343306|
+------------------+
-- csc
SELECT csc(1);
+------------------+
|            CSC(1)|
+------------------+
|1.1883951057781212|
+------------------+
-- degrees
SELECT degrees(3.141592653589793);
+--------------------------+
|DEGREES(3.141592653589793)|
+--------------------------+
|                     180.0|
+--------------------------+
-- div
SELECT 3 div 2;
+---------+
|(3 div 2)|
+---------+
|        1|
+---------+
SELECT INTERVAL '1-1' YEAR TO MONTH div INTERVAL '-1' MONTH;
+------------------------------------------------------+
|(INTERVAL '1-1' YEAR TO MONTH div INTERVAL '-1' MONTH)|
+------------------------------------------------------+
|                                                   -13|
+------------------------------------------------------+
-- e
SELECT e();
+-----------------+
|              E()|
+-----------------+
|2.718281828459045|
+-----------------+
-- exp
SELECT exp(0);
+------+
|EXP(0)|
+------+
|   1.0|
+------+
-- expm1
SELECT expm1(0);
+--------+
|EXPM1(0)|
+--------+
|     0.0|
+--------+
-- factorial
SELECT factorial(5);
+------------+
|factorial(5)|
+------------+
|         120|
+------------+
-- floor
SELECT floor(-0.1);
+-----------+
|FLOOR(-0.1)|
+-----------+
|         -1|
+-----------+
SELECT floor(5);
+--------+
|FLOOR(5)|
+--------+
|       5|
+--------+
SELECT floor(3.1411, 3);
+----------------+
|floor(3.1411, 3)|
+----------------+
|           3.141|
+----------------+
SELECT floor(3.1411, -3);
+-----------------+
|floor(3.1411, -3)|
+-----------------+
|                0|
+-----------------+
-- greatest
SELECT greatest(10, 9, 2, 4, 3);
+------------------------+
|greatest(10, 9, 2, 4, 3)|
+------------------------+
|                      10|
+------------------------+
-- hex
SELECT hex(17);
+-------+
|hex(17)|
+-------+
|     11|
+-------+
SELECT hex('SQL');
+------------------+
|    hex(SQL)|
+------------------+
|53514C|
+------------------+
-- hypot
SELECT hypot(3, 4);
+-----------+
|HYPOT(3, 4)|
+-----------+
|        5.0|
+-----------+
-- least
SELECT least(10, 9, 2, 4, 3);
+---------------------+
|least(10, 9, 2, 4, 3)|
+---------------------+
|                    2|
+---------------------+
-- ln
SELECT ln(1);
+-----+
|ln(1)|
+-----+
|  0.0|
+-----+
-- log
SELECT log(10, 100);
+------------+
|LOG(10, 100)|
+------------+
|         2.0|
+------------+
-- log10
SELECT log10(10);
+---------+
|LOG10(10)|
+---------+
|      1.0|
+---------+
-- log1p
SELECT log1p(0);
+--------+
|LOG1P(0)|
+--------+
|     0.0|
+--------+
-- log2
SELECT log2(2);
+-------+
|LOG2(2)|
+-------+
|    1.0|
+-------+
-- mod
SELECT 2 % 1.8;
+---------+
|(2 % 1.8)|
+---------+
|      0.2|
+---------+
SELECT MOD(2, 1.8);
+-----------+
|mod(2, 1.8)|
+-----------+
|        0.2|
+-----------+
-- negative
SELECT negative(1);
+-----------+
|negative(1)|
+-----------+
|         -1|
+-----------+
-- pi
SELECT pi();
+-----------------+
|             PI()|
+-----------------+
|3.141592653589793|
+-----------------+
-- pmod
SELECT pmod(10, 3);
+-----------+
|pmod(10, 3)|
+-----------+
|          1|
+-----------+
SELECT pmod(-10, 3);
+------------+
|pmod(-10, 3)|
+------------+
|           2|
+------------+
-- positive
SELECT positive(1);
+-----+
|(+ 1)|
+-----+
|    1|
+-----+
-- pow
SELECT pow(2, 3);
+---------+
|pow(2, 3)|
+---------+
|      8.0|
+---------+
-- power
SELECT power(2, 3);
+-----------+
|POWER(2, 3)|
+-----------+
|        8.0|
+-----------+
-- radians
SELECT radians(180);
+-----------------+
|     RADIANS(180)|
+-----------------+
|3.141592653589793|
+-----------------+
-- rand
SELECT rand();
+------------------+
|            rand()|
+------------------+
|0.7211420708112387|
+------------------+
SELECT rand(0);
+------------------+
|           rand(0)|
+------------------+
|0.7604953758285915|
+------------------+
SELECT rand(null);
+------------------+
|        rand(NULL)|
+------------------+
|0.7604953758285915|
+------------------+
-- randn
SELECT randn();
+-------------------+
|            randn()|
+-------------------+
|-0.8175603217732732|
+-------------------+
SELECT randn(0);
+------------------+
|          randn(0)|
+------------------+
|1.6034991609278433|
+------------------+
SELECT randn(null);
+------------------+
|       randn(NULL)|
+------------------+
|1.6034991609278433|
+------------------+
-- random
SELECT random();
+-----------------+
|           rand()|
+-----------------+
|0.394205008255365|
+-----------------+
SELECT random(0);
+------------------+
|           rand(0)|
+------------------+
|0.7604953758285915|
+------------------+
SELECT random(null);
+------------------+
|        rand(NULL)|
+------------------+
|0.7604953758285915|
+------------------+
-- rint
SELECT rint(12.3456);
+-------------+
|rint(12.3456)|
+-------------+
|         12.0|
+-------------+
-- round
SELECT round(2.5, 0);
+-------------+
|round(2.5, 0)|
+-------------+
|            3|
+-------------+
-- sec
SELECT sec(0);
+------+
|SEC(0)|
+------+
|   1.0|
+------+
-- shiftleft
SELECT shiftleft(2, 1);
+---------------+
|shiftleft(2, 1)|
+---------------+
|              4|
+---------------+
-- sign
SELECT sign(40);
+--------+
|sign(40)|
+--------+
|     1.0|
+--------+
SELECT sign(INTERVAL -'100' YEAR);
+--------------------------+
|sign(INTERVAL '-100' YEAR)|
+--------------------------+
|                      -1.0|
+--------------------------+
-- signum
SELECT signum(40);
+----------+
|SIGNUM(40)|
+----------+
|       1.0|
+----------+
SELECT signum(INTERVAL -'100' YEAR);
+----------------------------+
|SIGNUM(INTERVAL '-100' YEAR)|
+----------------------------+
|                        -1.0|
+----------------------------+
-- sin
SELECT sin(0);
+------+
|SIN(0)|
+------+
|   0.0|
+------+
-- sinh
SELECT sinh(0);
+-------+
|SINH(0)|
+-------+
|    0.0|
+-------+
-- sqrt
SELECT sqrt(4);
+-------+
|SQRT(4)|
+-------+
|    2.0|
+-------+
-- tan
SELECT tan(0);
+------+
|TAN(0)|
+------+
|   0.0|
+------+
-- tanh
SELECT tanh(0);
+-------+
|TANH(0)|
+-------+
|    0.0|
+-------+
-- try_add
SELECT try_add(1, 2);
+-------------+
|try_add(1, 2)|
+-------------+
|            3|
+-------------+
SELECT try_add(2147483647, 1);
+----------------------+
|try_add(2147483647, 1)|
+----------------------+
|                  NULL|
+----------------------+
SELECT try_add(date'2021-01-01', 1);
+-----------------------------+
|try_add(DATE '2021-01-01', 1)|
+-----------------------------+
|                   2021-01-02|
+-----------------------------+
SELECT try_add(date'2021-01-01', interval 1 year);
+---------------------------------------------+
|try_add(DATE '2021-01-01', INTERVAL '1' YEAR)|
+---------------------------------------------+
|                                   2022-01-01|
+---------------------------------------------+
SELECT try_add(timestamp'2021-01-01 00:00:00', interval 1 day);
+----------------------------------------------------------+
|try_add(TIMESTAMP '2021-01-01 00:00:00', INTERVAL '1' DAY)|
+----------------------------------------------------------+
|                                       2021-01-02 00:00:00|
+----------------------------------------------------------+
SELECT try_add(interval 1 year, interval 2 year);
+---------------------------------------------+
|try_add(INTERVAL '1' YEAR, INTERVAL '2' YEAR)|
+---------------------------------------------+
|                            INTERVAL '3' YEAR|
+---------------------------------------------+
-- try_divide
SELECT try_divide(3, 2);
+----------------+
|try_divide(3, 2)|
+----------------+
|             1.5|
+----------------+
SELECT try_divide(2L, 2L);
+----------------+
|try_divide(2, 2)|
+----------------+
|             1.0|
+----------------+
SELECT try_divide(1, 0);
+----------------+
|try_divide(1, 0)|
+----------------+
|            NULL|
+----------------+
SELECT try_divide(interval 2 month, 2);
+---------------------------------+
|try_divide(INTERVAL '2' MONTH, 2)|
+---------------------------------+
|             INTERVAL '0-1' YE...|
+---------------------------------+
SELECT try_divide(interval 2 month, 0);
+---------------------------------+
|try_divide(INTERVAL '2' MONTH, 0)|
+---------------------------------+
|                             NULL|
+---------------------------------+
-- try_multiply
SELECT try_multiply(2, 3);
+------------------+
|try_multiply(2, 3)|
+------------------+
|                 6|
+------------------+
SELECT try_multiply(-2147483648, 10);
+-----------------------------+
|try_multiply(-2147483648, 10)|
+-----------------------------+
|                         NULL|
+-----------------------------+
SELECT try_multiply(interval 2 year, 3);
+----------------------------------+
|try_multiply(INTERVAL '2' YEAR, 3)|
+----------------------------------+
|              INTERVAL '6-0' YE...|
+----------------------------------+
-- try_subtract
SELECT try_subtract(2, 1);
+------------------+
|try_subtract(2, 1)|
+------------------+
|                 1|
+------------------+
SELECT try_subtract(-2147483648, 1);
+----------------------------+
|try_subtract(-2147483648, 1)|
+----------------------------+
|                        NULL|
+----------------------------+
SELECT try_subtract(date'2021-01-02', 1);
+----------------------------------+
|try_subtract(DATE '2021-01-02', 1)|
+----------------------------------+
|                        2021-01-01|
+----------------------------------+
SELECT try_subtract(date'2021-01-01', interval 1 year);
+--------------------------------------------------+
|try_subtract(DATE '2021-01-01', INTERVAL '1' YEAR)|
+--------------------------------------------------+
|                                        2020-01-01|
+--------------------------------------------------+
SELECT try_subtract(timestamp'2021-01-02 00:00:00', interval 1 day);
+---------------------------------------------------------------+
|try_subtract(TIMESTAMP '2021-01-02 00:00:00', INTERVAL '1' DAY)|
+---------------------------------------------------------------+
|                                            2021-01-01 00:00:00|
+---------------------------------------------------------------+
SELECT try_subtract(interval 2 year, interval 1 year);
+--------------------------------------------------+
|try_subtract(INTERVAL '2' YEAR, INTERVAL '1' YEAR)|
+--------------------------------------------------+
|                                 INTERVAL '1' YEAR|
+--------------------------------------------------+
-- unhex
SELECT decode(unhex('53514C'), 'UTF-8');
+----------------------------------------+
|decode(unhex(53514C), UTF-8)|
+----------------------------------------+
|                               SQL|
+----------------------------------------+
-- width_bucket
SELECT width_bucket(5.3, 0.2, 10.6, 5);
+-------------------------------+
|width_bucket(5.3, 0.2, 10.6, 5)|
+-------------------------------+
|                              3|
+-------------------------------+
SELECT width_bucket(-2.1, 1.3, 3.4, 3);
+-------------------------------+
|width_bucket(-2.1, 1.3, 3.4, 3)|
+-------------------------------+
|                              0|
+-------------------------------+
SELECT width_bucket(8.1, 0.0, 5.7, 4);
+------------------------------+
|width_bucket(8.1, 0.0, 5.7, 4)|
+------------------------------+
|                             5|
+------------------------------+
SELECT width_bucket(-0.9, 5.2, 0.5, 2);
+-------------------------------+
|width_bucket(-0.9, 5.2, 0.5, 2)|
+-------------------------------+
|                              3|
+-------------------------------+
SELECT width_bucket(INTERVAL '0' YEAR, INTERVAL '0' YEAR, INTERVAL '10' YEAR, 10);
+--------------------------------------------------------------------------+
|width_bucket(INTERVAL '0' YEAR, INTERVAL '0' YEAR, INTERVAL '10' YEAR, 10)|
+--------------------------------------------------------------------------+
|                                                                         1|
+--------------------------------------------------------------------------+
SELECT width_bucket(INTERVAL '1' YEAR, INTERVAL '0' YEAR, INTERVAL '10' YEAR, 10);
+--------------------------------------------------------------------------+
|width_bucket(INTERVAL '1' YEAR, INTERVAL '0' YEAR, INTERVAL '10' YEAR, 10)|
+--------------------------------------------------------------------------+
|                                                                         2|
+--------------------------------------------------------------------------+
SELECT width_bucket(INTERVAL '0' DAY, INTERVAL '0' DAY, INTERVAL '10' DAY, 10);
+-----------------------------------------------------------------------+
|width_bucket(INTERVAL '0' DAY, INTERVAL '0' DAY, INTERVAL '10' DAY, 10)|
+-----------------------------------------------------------------------+
|                                                                      1|
+-----------------------------------------------------------------------+
SELECT width_bucket(INTERVAL '1' DAY, INTERVAL '0' DAY, INTERVAL '10' DAY, 10);
+-----------------------------------------------------------------------+
|width_bucket(INTERVAL '1' DAY, INTERVAL '0' DAY, INTERVAL '10' DAY, 10)|
+-----------------------------------------------------------------------+
|                                                                      2|
+-----------------------------------------------------------------------+
```

#### 生成器函数
<a name="supported-sql-generator"></a>

**注意**  
要查看哪些 AWS 数据源集成支持这些 SQL 函数，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。


****  

| 函数 | 说明 | 
| --- | --- | 
| explode(expr) | 将数组 `expr` 的元素拆分为多行，或将映射 `expr` 的元素拆分为多行多列。除非另有说明，否则数组元素默认使用列名 `col`，而映射元素默认使用 `key` 和 `value`。 | 
| explode\$1outer(expr) | 将数组 `expr` 的元素拆分为多行，或将映射 `expr` 的元素拆分为多行多列。除非另有说明，否则数组元素默认使用列名 `col`，而映射元素默认使用 `key` 和 `value`。 | 
| inline(expr) | 将结构数组展开为表。除非另有说明，否则默认使用列名 col1、col2 等。 | 
| inline\$1outer(expr) | 将结构数组展开为表。除非另有说明，否则默认使用列名 col1、col2 等。 | 
| posexplode(expr) | 将数组 `expr` 的元素按位置拆分为多行，或将映射 `expr` 的元素按位置拆分为多行多列。除非另有说明，否则使用列名 `pos` 表示位置，`col` 表示数组元素，`key` 和 `value` 表示映射元素。 | 
| posexplode\$1outer(expr) | 将数组 `expr` 的元素按位置拆分为多行，或将映射 `expr` 的元素按位置拆分为多行多列。除非另有说明，否则使用列名 `pos` 表示位置，`col` 表示数组元素，`key` 和 `value` 表示映射元素。 | 
| stack(n, expr1, ..., exprk) | 将 `expr1`、...、`exprk` 拆分为 `n` 行。除非另有说明，否则默认使用列名 col0、col1 等。 | 

**示例**

```
-- explode
SELECT explode(array(10, 20));
+---+
|col|
+---+
| 10|
| 20|
+---+

SELECT explode(collection => array(10, 20));
+---+
|col|
+---+
| 10|
| 20|
+---+

SELECT * FROM explode(collection => array(10, 20));
+---+
|col|
+---+
| 10|
| 20|
+---+

-- explode_outer
SELECT explode_outer(array(10, 20));
+---+
|col|
+---+
| 10|
| 20|
+---+

SELECT explode_outer(collection => array(10, 20));
+---+
|col|
+---+
| 10|
| 20|
+---+

SELECT * FROM explode_outer(collection => array(10, 20));
+---+
|col|
+---+
| 10|
| 20|
+---+

-- inline
SELECT inline(array(struct(1, 'a'), struct(2, 'b')));
+----+----+
|col1|col2|
+----+----+
|   1|   a|
|   2|   b|
+----+----+

-- inline_outer
SELECT inline_outer(array(struct(1, 'a'), struct(2, 'b')));
+----+----+
|col1|col2|
+----+----+
|   1|   a|
|   2|   b|
+----+----+

-- posexplode
SELECT posexplode(array(10,20));
+---+---+
|pos|col|
+---+---+
|  0| 10|
|  1| 20|
+---+---+

SELECT * FROM posexplode(array(10,20));
+---+---+
|pos|col|
+---+---+
|  0| 10|
|  1| 20|
+---+---+

-- posexplode_outer
SELECT posexplode_outer(array(10,20));
+---+---+
|pos|col|
+---+---+
|  0| 10|
|  1| 20|
+---+---+

SELECT * FROM posexplode_outer(array(10,20));
+---+---+
|pos|col|
+---+---+
|  0| 10|
|  1| 20|
+---+---+

-- stack
SELECT stack(2, 1, 2, 3);
+----+----+
|col0|col1|
+----+----+
|   1|   2|
|   3|NULL|
+----+----+
```

#### SELECT 子句
<a name="supported-sql-select"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

OpenSearch SQL 支持用于从一个或多个表中检索结果集的`SELECT`语句。以下部分描述查询的整体语法及其不同构造。

**语法** 

```
select_statement 
[ { UNION | INTERSECT | EXCEPT } [ ALL | DISTINCT ] select_statement, ... ]
[ ORDER BY 
    { expression [ ASC | DESC ] [ NULLS { FIRST | LAST } ] 
    [ , ... ] 
    } 
]
[ SORT BY 
    { expression [ ASC | DESC ] [ NULLS { FIRST | LAST } ] 
    [ , ... ] 
    } 
]
[ WINDOW { named_window [ , WINDOW named_window, ... ] } ]
[ LIMIT { ALL | expression } ]
```

当 `select_statement` 定义为：

```
SELECT [ ALL | DISTINCT ] { [ [ named_expression ] [ , ... ] ] }
FROM { from_item [ , ... ] }
[ PIVOT clause ]
[ UNPIVOT clause ]
[ LATERAL VIEW clause ] [ ... ]
[ WHERE boolean_expression ]
[ GROUP BY expression [ , ... ] ]
[ HAVING boolean_expression ]
```

 **参数** 
+ **全部** 

  从关系中选择所有匹配的行，默认处于启用状态。
+ **DISTINCT** 

  移除结果中的重复项后，从关系中选择所有匹配的行。
+ **named\$1expression**

  具有指定名称的表达式。通常表示列表达式。

  语法：`expression [[AS] alias]`
+ **from\$1item**

  表关系

  关联关系

  转置关系

  逆透视关系

  表值函数

  内联表

  `[ LATERAL ] ( Subquery )`
+ **PIVOT** 

  `PIVOT` 子句用于数据透视。您可以根据特定列值获取聚合值。
+ **UNPIVOT** 

  `UNPIVOT` 子句将列转换为行。与 `PIVOT` 相反，但值的聚合除外。
+ **LATERAL VIEW**

  `LATERAL VIEW` 子句与生成器函数（例如 `EXPLODE`）结合使用，后者将生成包含一行或多行的虚拟表。

  `LATERAL VIEW` 会将这些行应用于每个原始输出行。
+ **WHERE** 

  根据提供的谓词筛选 `FROM` 子句的结果。
+ **GROUP BY**

  指定用于对行进行分组的表达式。

  这与聚合函数（`MIN`、`MAX`、`COUNT`、`SUM`、`AVG` 等）结合使用，根据分组表达式对行进行分组，并在每个组内计算聚合值。

  将 `FILTER` 子句附加到聚合函数时，仅将匹配的行传递给该函数。
+ **有** 

  指定用于筛选由 `GROUP BY` 生成的行所依据的谓词。

  `HAVING` 子句用于在分组操作完成后筛选行。

  如果未指定不含 `GROUP BY` 的 `HAVING`，则表示不含分组表达式的 `GROUP BY`（全局聚合）。
+ **ORDER BY**

  指定查询完整结果集的行排序顺序。

  输出行按分区进行排序。

  此参数与 `SORT BY` 和 `DISTRIBUTE BY` 互斥，不可同时指定。
+ **SORT BY**

  指定每个分区中行的排序顺序。

  此参数与 `ORDER BY` 互斥，不可同时指定。
+ **LIMIT** 

  指定语句或子查询可返回的最大行数。

  此子句主要与 `ORDER BY` 结合使用，以产生确定性结果。
+ **boolean\$1expression**

  指定任何评估结果为布尔值的表达式。

  两个或多个表达式可使用逻辑运算符（`AND`、`OR`）进行组合。
+ **expression** 

  指定一个或多个值、运算符和计算结果为值的 SQL 函数的组合。
+ **named\$1window**

  指定一个或多个源窗口规格的别名。

  可以在查询的窗口定义中引用源窗口规格。

#### WHERE 子句
<a name="supported-sql-where"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

`WHERE` 子句用于根据指定条件限制查询或子查询中 `FROM` 子句的结果。

**语法** 

```
WHERE boolean_expression
```

**参数**
+ **boolean\$1expression** 

  指定任何评估结果为布尔值的表达式。

  两个或多个表达式可使用逻辑运算符（`AND`、`OR`）进行组合。

**示例**

```
CREATE TABLE person (id INT, name STRING, age INT);
INSERT INTO person VALUES
(100, 'John', 30),
(200, 'Mary', NULL),
(300, 'Mike', 80),
(400, 'Dan',  50);

-- Comparison operator in `WHERE` clause.
SELECT * FROM person WHERE id > 200 ORDER BY id;
+---+----+---+
| id|name|age|
+---+----+---+
|300|Mike| 80|
|400| Dan| 50|
+---+----+---+

-- Comparison and logical operators in `WHERE` clause.
SELECT * FROM person WHERE id = 200 OR id = 300 ORDER BY id;
+---+----+----+
| id|name| age|
+---+----+----+
|200|Mary|null|
|300|Mike|  80|
+---+----+----+

-- IS NULL expression in `WHERE` clause.
SELECT * FROM person WHERE id > 300 OR age IS NULL ORDER BY id;
+---+----+----+
| id|name| age|
+---+----+----+
|200|Mary|null|
|400| Dan|  50|
+---+----+----+

-- Function expression in `WHERE` clause.
SELECT * FROM person WHERE length(name) > 3 ORDER BY id;
+---+----+----+
| id|name| age|
+---+----+----+
|100|John|  30|
|200|Mary|null|
|300|Mike|  80|
+---+----+----+

-- `BETWEEN` expression in `WHERE` clause.
SELECT * FROM person WHERE id BETWEEN 200 AND 300 ORDER BY id;
+---+----+----+
| id|name| age|
+---+----+----+
|200|Mary|null|
|300|Mike|  80|
+---+----+----+

-- Scalar Subquery in `WHERE` clause.
SELECT * FROM person WHERE age > (SELECT avg(age) FROM person);
+---+----+---+
| id|name|age|
+---+----+---+
|300|Mike| 80|
+---+----+---+
 
-- Correlated Subquery in `WHERE` clause.
SELECT id FROM person
WHERE exists (SELECT id FROM person where id = 200);
+---+----+----+
|id |name|age |
+---+----+----+
|200|Mary|null|
+---+----+----+
```

#### GROUP BY 子句
<a name="supported-sql-group-by"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

`GROUP BY` 子句用于根据一组指定的分组表达式对行进行分组，并基于一个或多个指定的聚合函数对分组后的行进行聚合计算。

系统还通过 `GROUPING SETS`、`CUBE`、`ROLLUP` 子句对同一输入记录集执行多重聚合操作。分组表达式和高级聚合可在 `GROUP BY` 子句中混合使用，也可以嵌套在 `GROUPING SETS ` 子句中。有关更多详细信息，请参阅 `Mixed/Nested Grouping Analytics ` 一节。

将 `FILTER` 子句附加到聚合函数时，仅将匹配的行传递给该函数。

**语法** 

```
GROUP BY group_expression [ , group_expression [ , ... ] ] [ WITH { ROLLUP | CUBE } ]
GROUP BY { group_expression | { ROLLUP | CUBE | GROUPING SETS } (grouping_set [ , ...]) } [ , ... ]
```

聚合函数定义为：

```
aggregate_name ( [ DISTINCT ] expression [ , ... ] ) [ FILTER ( WHERE boolean_expression ) ]
```

**参数**
+ **group\$1expression**

  指定用于将行分组的标准。根据分组表达式的结果值对行进行分组。

  分组表达式可以是列名（如 `GROUP BY a`）、列位置（如 `GROUP BY 0`）或表达式（如 `GROUP BY a + b`）。
+ **grouping\$1set**

  分组集由零个或多个用逗号分隔的括号表达式指定。当分组集仅包含一个元素时，可以省略括号。

  例如，`GROUPING SETS ((a), (b))` 与 `GROUPING SETS (a, b)` 相同。

  语法：`{ ( [ expression [ , ... ] ] ) | expression }`
+ **GROUPING SETS**

  将行按 `GROUPING SETS` 之后指定的每个分组集进行分组。

  例如，`GROUP BY GROUPING SETS ((warehouse), (product))` 在语义上等同于 `GROUP BY warehouse` 和 `GROUP BY product` 的结果并集。此子句是 UNION ALL 的简写形式，其中 `UNION ALL` 运算符的每个分支对 `GROUPING SETS` 子句中指定的每个分组集进行聚合。

  同样，`GROUP BY GROUPING SETS ((warehouse, product), (product), ())` 在语义上等同于 `GROUP BY warehouse, product, GROUP BY product` 和全局聚合的结果并集。
+ **ROLLUP** 

  在单个语句中指定多级聚合操作。此子句用于计算基于多个分组集的聚合。`ROLLUP` 是 `GROUPING SETS` 的简写形式。

  例如，`GROUP BY warehouse, product WITH ROLLUP or GROUP BY ROLLUP(warehouse, product)` 等同于 `GROUP BY GROUPING SETS((warehouse, product), (warehouse), ())`。

  `GROUP BY ROLLUP(warehouse, product, (warehouse, location))` 等同于 `GROUP BY GROUPING SETS((warehouse, product, location), (warehouse, product), (warehouse), ())`。

  ROLLUP 规范的 N 个元素会生成 N\$11 个分组集。
+ **CUBE** 

  CUBE 子句用于根据 GROUP BY 子句中指定的分组列组合执行聚合操作。CUBE 是 GROUPING SETS 的简写形式。

  例如，`GROUP BY warehouse, product WITH CUBE or GROUP BY CUBE(warehouse, product)` 等同于 `GROUP BY GROUPING SETS((warehouse, product), (warehouse), (product), ())`。

  `GROUP BY CUBE(warehouse, product, (warehouse, location))` 等同于 `GROUP BY GROUPING SETS((warehouse, product, location), (warehouse, product), (warehouse, location), (product, warehouse, location), (warehouse), (product), (warehouse, product), ())`。`CUBE` 规范的 N 个元素会生成 2^N 个 `GROUPING SETS`。
+ **混合/嵌套分组分析**

  `GROUP BY` 子句可以包含多个 group\$1expressions 和多个 `CUBE|ROLLUP|GROUPING SETS`。`GROUPING SETS` 也可以包含嵌套的 `CUBE|ROLLUP|GROUPING SETS` 子句，例如 `GROUPING SETS(ROLLUP(warehouse, location)`、`CUBE(warehouse, location))`、`GROUPING SETS(warehouse, GROUPING SETS(location, GROUPING SETS(ROLLUP(warehouse, location),`、`CUBE(warehouse, location))))`。

  `CUBE|ROLLUP` 只是 `GROUPING SETS` 的语法糖。关于如何将 `CUBE|ROLLUP` 转换为 `GROUPING SETS`，请参阅上述章节。在此语境下，`group_expression` 可视为单一组 `GROUPING SETS`。

  对于 `GROUP BY` 子句中的多个 `GROUPING SETS`，我们通过对原始 `GROUPING SETS` 进行交叉运算生成单个 `GROUPING SETS`。对于 `GROUPING SETS` 子句中的嵌套 `GROUPING SETS`，我们只需提取其分组集并将其去除。

  例如，`GROUP BY warehouse, GROUPING SETS((product), ()), GROUPING SETS((location, size), (location), (size), ()) and GROUP BY warehouse, ROLLUP(product), CUBE(location, size)` 等同于 `GROUP BY GROUPING SETS( (warehouse, product, location, size), (warehouse, product, location), (warehouse, product, size), (warehouse, product), (warehouse, location, size), (warehouse, location), (warehouse, size), (warehouse))`。

  `GROUP BY GROUPING SETS(GROUPING SETS(warehouse), GROUPING SETS((warehouse, product)))` 等同于 `GROUP BY GROUPING SETS((warehouse), (warehouse, product))`。
+ **aggregate\$1name**

  指定聚合函数名称（`MIN`、`MAX`、`COUNT`、`SUM`、`AVG` 等）。
+ **DISTINCT** 

  在将输入行传递给聚合函数之前，移除其中的重复项。
+ **过滤器** 

  筛选输入行，其中 `WHERE` 子句中 `boolean_expression` 计算结果为 true 时，该行将传递给聚合函数；其余行将被丢弃。

**示例**

```
CREATE TABLE dealer (id INT, city STRING, car_model STRING, quantity INT);
INSERT INTO dealer VALUES
(100, 'Fremont', 'Honda Civic', 10),
(100, 'Fremont', 'Honda Accord', 15),
(100, 'Fremont', 'Honda CRV', 7),
(200, 'Dublin', 'Honda Civic', 20),
(200, 'Dublin', 'Honda Accord', 10),
(200, 'Dublin', 'Honda CRV', 3),
(300, 'San Jose', 'Honda Civic', 5),
(300, 'San Jose', 'Honda Accord', 8);

-- Sum of quantity per dealership. Group by `id`.
SELECT id, sum(quantity) FROM dealer GROUP BY id ORDER BY id;
+---+-------------+
| id|sum(quantity)|
+---+-------------+
|100|           32|
|200|           33|
|300|           13|
+---+-------------+

-- Use column position in GROUP by clause.
SELECT id, sum(quantity) FROM dealer GROUP BY 1 ORDER BY 1;
+---+-------------+
| id|sum(quantity)|
+---+-------------+
|100|           32|
|200|           33|
|300|           13|
+---+-------------+

-- Multiple aggregations.
-- 1. Sum of quantity per dealership.
-- 2. Max quantity per dealership.
SELECT id, sum(quantity) AS sum, max(quantity) AS max FROM dealer GROUP BY id ORDER BY id;
+---+---+---+
| id|sum|max|
+---+---+---+
|100| 32| 15|
|200| 33| 20|
|300| 13|  8|
+---+---+---+

-- Count the number of distinct dealer cities per car_model.
SELECT car_model, count(DISTINCT city) AS count FROM dealer GROUP BY car_model;
+------------+-----+
|   car_model|count|
+------------+-----+
| Honda Civic|    3|
|   Honda CRV|    2|
|Honda Accord|    3|
+------------+-----+

-- Sum of only 'Honda Civic' and 'Honda CRV' quantities per dealership.
SELECT id, sum(quantity) FILTER (
WHERE car_model IN ('Honda Civic', 'Honda CRV')
) AS `sum(quantity)` FROM dealer
GROUP BY id ORDER BY id;
+---+-------------+
| id|sum(quantity)|
+---+-------------+
|100|           17|
|200|           23|
|300|            5|
+---+-------------+

-- Aggregations using multiple sets of grouping columns in a single statement.
-- Following performs aggregations based on four sets of grouping columns.
-- 1. city, car_model
-- 2. city
-- 3. car_model
-- 4. Empty grouping set. Returns quantities for all city and car models.
SELECT city, car_model, sum(quantity) AS sum FROM dealer
GROUP BY GROUPING SETS ((city, car_model), (city), (car_model), ())
ORDER BY city;
+---------+------------+---+
|     city|   car_model|sum|
+---------+------------+---+
|     null|        null| 78|
|     null| HondaAccord| 33|
|     null|    HondaCRV| 10|
|     null|  HondaCivic| 35|
|   Dublin|        null| 33|
|   Dublin| HondaAccord| 10|
|   Dublin|    HondaCRV|  3|
|   Dublin|  HondaCivic| 20|
|  Fremont|        null| 32|
|  Fremont| HondaAccord| 15|
|  Fremont|    HondaCRV|  7|
|  Fremont|  HondaCivic| 10|
| San Jose|        null| 13|
| San Jose| HondaAccord|  8|
| San Jose|  HondaCivic|  5|
+---------+------------+---+

-- Group by processing with `ROLLUP` clause.
-- Equivalent GROUP BY GROUPING SETS ((city, car_model), (city), ())
SELECT city, car_model, sum(quantity) AS sum FROM dealer
GROUP BY city, car_model WITH ROLLUP
ORDER BY city, car_model;
+---------+------------+---+
|     city|   car_model|sum|
+---------+------------+---+
|     null|        null| 78|
|   Dublin|        null| 33|
|   Dublin| HondaAccord| 10|
|   Dublin|    HondaCRV|  3|
|   Dublin|  HondaCivic| 20|
|  Fremont|        null| 32|
|  Fremont| HondaAccord| 15|
|  Fremont|    HondaCRV|  7|
|  Fremont|  HondaCivic| 10|
| San Jose|        null| 13|
| San Jose| HondaAccord|  8|
| San Jose|  HondaCivic|  5|
+---------+------------+---+

-- Group by processing with `CUBE` clause.
-- Equivalent GROUP BY GROUPING SETS ((city, car_model), (city), (car_model), ())
SELECT city, car_model, sum(quantity) AS sum FROM dealer
GROUP BY city, car_model WITH CUBE
ORDER BY city, car_model;
+---------+------------+---+
|     city|   car_model|sum|
+---------+------------+---+
|     null|        null| 78|
|     null| HondaAccord| 33|
|     null|    HondaCRV| 10|
|     null|  HondaCivic| 35|
|   Dublin|        null| 33|
|   Dublin| HondaAccord| 10|
|   Dublin|    HondaCRV|  3|
|   Dublin|  HondaCivic| 20|
|  Fremont|        null| 32|
|  Fremont| HondaAccord| 15|
|  Fremont|    HondaCRV|  7|
|  Fremont|  HondaCivic| 10|
| San Jose|        null| 13|
| San Jose| HondaAccord|  8|
| San Jose|  HondaCivic|  5|
+---------+------------+---+

--Prepare data for ignore nulls example
CREATE TABLE person (id INT, name STRING, age INT);
INSERT INTO person VALUES
(100, 'Mary', NULL),
(200, 'John', 30),
(300, 'Mike', 80),
(400, 'Dan', 50);

--Select the first row in column age
SELECT FIRST(age) FROM person;
+--------------------+
| first(age, false)  |
+--------------------+
| NULL               |
+--------------------+

--Get the first row in column `age` ignore nulls,last row in column `id` and sum of column `id`.
SELECT FIRST(age IGNORE NULLS), LAST(id), SUM(id) FROM person;
+-------------------+------------------+----------+
| first(age, true)  | last(id, false)  | sum(id)  |
+-------------------+------------------+----------+
| 30                | 400              | 1000     |
+-------------------+------------------+----------+
```

#### HAVING 子句
<a name="supported-sql-having"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

`HAVING` 子句用于根据指定条件筛选 `GROUP BY` 生成的结果。该子句通常与 `GROUP BY` 子句搭配使用。

**语法** 

```
HAVING boolean_expression
```

**参数**
+ **boolean\$1expression**

  指定任何评估结果为布尔值的表达式。两个或多个表达式可使用逻辑运算符（`AND`、`OR`）进行组合。

  **注意**，`HAVING` 子句中指定的表达式只能指：

  1. 常量 

  1. `GROUP BY` 中出现的表达式 

  1. 聚合函数 

**示例**

```
CREATE TABLE dealer (id INT, city STRING, car_model STRING, quantity INT);
INSERT INTO dealer VALUES
(100, 'Fremont', 'Honda Civic', 10),
(100, 'Fremont', 'Honda Accord', 15),
(100, 'Fremont', 'Honda CRV', 7),
(200, 'Dublin', 'Honda Civic', 20),
(200, 'Dublin', 'Honda Accord', 10),
(200, 'Dublin', 'Honda CRV', 3),
(300, 'San Jose', 'Honda Civic', 5),
(300, 'San Jose', 'Honda Accord', 8);

-- `HAVING` clause referring to column in `GROUP BY`.
SELECT city, sum(quantity) AS sum FROM dealer GROUP BY city HAVING city = 'Fremont';
+-------+---+
|   city|sum|
+-------+---+
|Fremont| 32|
+-------+---+

-- `HAVING` clause referring to aggregate function.
SELECT city, sum(quantity) AS sum FROM dealer GROUP BY city HAVING sum(quantity) > 15;
+-------+---+
|   city|sum|
+-------+---+
| Dublin| 33|
|Fremont| 32|
+-------+---+

-- `HAVING` clause referring to aggregate function by its alias.
SELECT city, sum(quantity) AS sum FROM dealer GROUP BY city HAVING sum > 15;
+-------+---+
|   city|sum|
+-------+---+
| Dublin| 33|
|Fremont| 32|
+-------+---+

-- `HAVING` clause referring to a different aggregate function than what is present in
-- `SELECT` list.
SELECT city, sum(quantity) AS sum FROM dealer GROUP BY city HAVING max(quantity) > 15;
+------+---+
|  city|sum|
+------+---+
|Dublin| 33|
+------+---+

-- `HAVING` clause referring to constant expression.
SELECT city, sum(quantity) AS sum FROM dealer GROUP BY city HAVING 1 > 0 ORDER BY city;
+--------+---+
|    city|sum|
+--------+---+
|  Dublin| 33|
| Fremont| 32|
|San Jose| 13|
+--------+---+

-- `HAVING` clause without a `GROUP BY` clause.
SELECT sum(quantity) AS sum FROM dealer HAVING sum(quantity) > 10;
+---+
|sum|
+---+
| 78|
+---+
```

#### ORDER BY 子句
<a name="supported-sql-order-by"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

`ORDER BY` 子句用于按用户指定的顺序返回排序后的结果行。与 SORT BY 子句不同，该子句保证输出结果具有全序关系。

**语法** 

```
ORDER BY { expression [ sort_direction | nulls_sort_order ] [ , ... ] }
```

**参数**
+ **ORDER BY**

  指定用逗号分隔的表达式列表以及用于对行进行排序的可选参数 `sort_direction` 和 `nulls_sort_order`。
+ **sort\$1direction**

  （可选）指定是按升序还是降序对行进行排序。

  排序方向的有效值为 `ASC` 表示升序，`DESC` 表示降序。

  如果未明确指定排序方向，则默认按升序对行进行排序。

  语法：`[ ASC | DESC ] `
+ **nulls\$1sort\$1order**

  （可选）指定`NULL`值是否返回 before/after 非 NULL 值。

  如果未指定 null\$1sort\$1order，如果排序顺序为 `ASC`，则 `NULLs` 排在最前；如果排序顺序为 `DESC`，则 NULL 排在最后。

  1. 如果已指定 `NULLS FIRST`，则无论排序顺序如何，都将首先返回 NULL 值。

  2. 如果已指定 `NULLS LAST`，则无论排序顺序如何，都将最后返回 NULL 值。

  语法：`[ NULLS { FIRST | LAST } ]`

**示例**

```
CREATE TABLE person (id INT, name STRING, age INT);
INSERT INTO person VALUES
(100, 'John', 30),
(200, 'Mary', NULL),
(300, 'Mike', 80),
(400, 'Jerry', NULL),
(500, 'Dan',  50);

-- Sort rows by age. By default rows are sorted in ascending manner with NULL FIRST.
SELECT name, age FROM person ORDER BY age;
+-----+----+
| name| age|
+-----+----+
|Jerry|null|
| Mary|null|
| John|  30|
|  Dan|  50|
| Mike|  80|
+-----+----+

-- Sort rows in ascending manner keeping null values to be last.
SELECT name, age FROM person ORDER BY age NULLS LAST;
+-----+----+
| name| age|
+-----+----+
| John|  30|
|  Dan|  50|
| Mike|  80|
| Mary|null|
|Jerry|null|
+-----+----+

-- Sort rows by age in descending manner, which defaults to NULL LAST.
SELECT name, age FROM person ORDER BY age DESC;
+-----+----+
| name| age|
+-----+----+
| Mike|  80|
|  Dan|  50|
| John|  30|
|Jerry|null|
| Mary|null|
+-----+----+

-- Sort rows in ascending manner keeping null values to be first.
SELECT name, age FROM person ORDER BY age DESC NULLS FIRST;
+-----+----+
| name| age|
+-----+----+
|Jerry|null|
| Mary|null|
| Mike|  80|
|  Dan|  50|
| John|  30|
+-----+----+

-- Sort rows based on more than one column with each column having different
-- sort direction.
SELECT * FROM person ORDER BY name ASC, age DESC;
+---+-----+----+
| id| name| age|
+---+-----+----+
|500|  Dan|  50|
|400|Jerry|null|
|100| John|  30|
|200| Mary|null|
|300| Mike|  80|
+---+-----+----+
```

#### JOIN 子句
<a name="supported-sql-join"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

SQL 联接用于根据联接标准合并两个关系中的行。以下部分将介绍整体联接语法、不同类型的联接及其示例。

**语法** 

```
relation INNER JOIN relation [ join_criteria ]
```

**参数**
+ **relation**

  指定要联接的关系。
+ **join\$1type**

  指定联接类型。

  语法：`INNER | CROSS | LEFT OUTER`
+ **join\$1criteria**

  指定如何将一个关系中的行与另一个关系的行进行合并。

  语法：`ON boolean_expression | USING ( column_name [ , ... ] ) `
+ **boolean\$1expression**

  指定返回类型为布尔值的表达式。

**联接类型**
+ **内联接**

  内联接需显式指定。内联接选择在两个关系中都具有匹配值的行。

  语法：`relation INNER JOIN relation [ join_criteria ] `
+ **左联接**

  左联接返回左侧关系中的所有值以及右侧关系中的匹配值，如果不存在匹配项，则附加 NULL。也称为左外联接。

  语法：`relation LEFT OUTER JOIN relation [ join_criteria ]`
+ **交叉联接**

  交叉联接返回两个关系的笛卡尔乘积。

  语法：`relation CROSS JOIN relation [ join_criteria ]`

**示例**

```
-- Use employee and department tables to demonstrate different type of joins.
SELECT * FROM employee;
+---+-----+------+
| id| name|deptno|
+---+-----+------+
|105|Chloe|     5|
|103| Paul|     3|
|101| John|     1|
|102| Lisa|     2|
|104| Evan|     4|
|106|  Amy|     6|
+---+-----+------+
SELECT * FROM department;
+------+-----------+
|deptno|   deptname|
+------+-----------+
|     3|Engineering|
|     2|      Sales|
|     1|  Marketing|
+------+-----------+

-- Use employee and department tables to demonstrate inner join.
SELECT id, name, employee.deptno, deptname
FROM employee INNER JOIN department ON employee.deptno = department.deptno;
+---+-----+------+-----------|
| id| name|deptno|   deptname|
+---+-----+------+-----------|
|103| Paul|     3|Engineering|
|101| John|     1|  Marketing|
|102| Lisa|     2|      Sales|
+---+-----+------+-----------|

-- Use employee and department tables to demonstrate left join.
SELECT id, name, employee.deptno, deptname
FROM employee LEFT JOIN department ON employee.deptno = department.deptno;
+---+-----+------+-----------|
| id| name|deptno|   deptname|
+---+-----+------+-----------|
|105|Chloe|     5|       NULL|
|103| Paul|     3|Engineering|
|101| John|     1|  Marketing|
|102| Lisa|     2|      Sales|
|104| Evan|     4|       NULL|
|106|  Amy|     6|       NULL|
+---+-----+------+-----------|

-- Use employee and department tables to demonstrate cross join.
SELECT id, name, employee.deptno, deptname FROM employee CROSS JOIN department;
+---+-----+------+-----------|
| id| name|deptno|   deptname|
+---+-----+------+-----------|
|105|Chloe|     5|Engineering|
|105|Chloe|     5|  Marketing|
|105|Chloe|     5|      Sales|
|103| Paul|     3|Engineering|
|103| Paul|     3|  Marketing|
|103| Paul|     3|      Sales|
|101| John|     1|Engineering|
|101| John|     1|  Marketing|
|101| John|     1|      Sales|
|102| Lisa|     2|Engineering|
|102| Lisa|     2|  Marketing|
|102| Lisa|     2|      Sales|
|104| Evan|     4|Engineering|
|104| Evan|     4|  Marketing|
|104| Evan|     4|      Sales|
|106|  Amy|     4|Engineering|
|106|  Amy|     4|  Marketing|
|106|  Amy|     4|      Sales|
+---+-----+------+-----------|
```

#### LIMIT 子句
<a name="supported-sql-limit"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

`LIMIT` 子句用于限制 `SELECT` 语句返回的行数。通常，该子句需与 `ORDER BY` 配合使用，以确保结果具有确定性。

**语法** 

```
LIMIT { ALL | integer_expression }
```

**参数**
+ **全部**

  如果指定，则查询返回所有行。换言之，如果指定此项，则不应用任何限制。
+ **integer\$1expression**

  指定返回整数的可折叠表达式。

**示例**

```
CREATE TABLE person (name STRING, age INT);
INSERT INTO person VALUES
('Jane Doe', 25),
('Pat C', 18),
('Nikki W', 16),
('John D', 25),
('Juan L', 18),
('Jorge S', 16);

-- Select the first two rows.
SELECT name, age FROM person ORDER BY name LIMIT 2;
+-------+---+
|   name|age|
+-------+---+
|  Pat C| 18|
|Jorge S| 16|
+------+---+

-- Specifying ALL option on LIMIT returns all the rows.
SELECT name, age FROM person ORDER BY name LIMIT ALL;
+--------+---+
|    name|age|
+--------+---+
|   Pat C| 18|
| Jorge S| 16|
|  Juan L| 18|
|  John D| 25|
| Nikki W| 16|
|Jane Doe| 25|
+--------+---+

-- A function expression as an input to LIMIT.
SELECT name, age FROM person ORDER BY name LIMIT length('OPENSEARCH');
+-------+---+
|   name|age|
+-------+---+
|  Pat C| 18|
|Jorge S| 16|
| Juan L| 18|
| John D| 25|
|Nikki W| 16|
+-------+---+
```

#### CASE 子句
<a name="supported-sql-case"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

`CASE` 子句使用规则根据指定条件返回特定结果，类似于其他编程语言中的 if/else 语句。

**语法** 

```
CASE [ expression ] { WHEN boolean_expression THEN then_expression } [ ... ]
[ ELSE else_expression ]
END
```

**参数**
+ **boolean\$1expression**

  指定任何评估结果为布尔值的表达式。

  两个或多个表达式可使用逻辑运算符（`AND`、`OR`）进行组合。
+ **then\$1expression**

  根据 boolean\$1expression 条件指定 then 表达式。

  `then_expression` 和 `else_expression` 应为相同类型或可强制转换为共同类型。
+ **else\$1expression**

  指定默认表达式。

  `then_expression` 和 ` else_expression` 应为相同类型或可强制转换为共同类型。

**示例**

```
CREATE TABLE person (id INT, name STRING, age INT);
INSERT INTO person VALUES
(100, 'John', 30),
(200, 'Mary', NULL),
(300, 'Mike', 80),
(400, 'Dan', 50);
SELECT id, CASE WHEN id > 200 THEN 'bigger' ELSE 'small' END FROM person;
+------+--------------------------------------------------+
|  id  | CASE WHEN (id > 200) THEN bigger ELSE small END  |
+------+--------------------------------------------------+
| 100  | small                                            |
| 200  | small                                            |
| 300  | bigger                                           |
| 400  | bigger                                           |
+------+--------------------------------------------------+
SELECT id, CASE id WHEN 100 then 'bigger' WHEN  id > 300 THEN '300' ELSE 'small' END FROM person;
+------+-----------------------------------------------------------------------------------------------+
|  id  | CASE WHEN (id = 100) THEN bigger WHEN (id = CAST((id > 300) AS INT)) THEN 300 ELSE small END  |
+------+-----------------------------------------------------------------------------------------------+
| 100  | bigger                                                                                        |
| 200  | small                                                                                         |
| 300  | small                                                                                         |
| 400  | small                                                                                         |
+------+-----------------------------------------------------------------------------------------------+
```

#### 公用表表达式
<a name="supported-sql-cte"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

公用表表达式（CTE）定义临时结果集，用户可在 SQL 语句作用域内多次引用该结果集。CTE 主要用于 `SELECT` 语句。

**语法** 

```
WITH common_table_expression [ , ... ]
```

当 `common_table_expression` 定义为：

```
Syntexpression_name [ ( column_name [ , ... ] ) ] [ AS ] ( query )
```

**参数** 
+ **expression\$1name**

  指定公用表表达式的名称。
+ **query** 

  `SELECT` 语句。

**示例**

```
-- CTE with multiple column aliases
WITH t(x, y) AS (SELECT 1, 2)
SELECT * FROM t WHERE x = 1 AND y = 2;
+---+---+
|  x|  y|
+---+---+
|  1|  2|
+---+---+

-- CTE in CTE definition
WITH t AS (
WITH t2 AS (SELECT 1)
SELECT * FROM t2
)
SELECT * FROM t;
+---+
|  1|
+---+
|  1|
+---+

-- CTE in subquery
SELECT max(c) FROM (
WITH t(c) AS (SELECT 1)
SELECT * FROM t
);
+------+
|max(c)|
+------+
|     1|
+------+

-- CTE in subquery expression
SELECT (
WITH t AS (SELECT 1)
SELECT * FROM t
);
+----------------+
|scalarsubquery()|
+----------------+
|               1|
+----------------+

-- CTE in CREATE VIEW statement
CREATE VIEW v AS
WITH t(a, b, c, d) AS (SELECT 1, 2, 3, 4)
SELECT * FROM t;
SELECT * FROM v;
+---+---+---+---+
|  a|  b|  c|  d|
+---+---+---+---+
|  1|  2|  3|  4|
+---+---+---+---+
```

#### EXPLAIN
<a name="supported-sql-explain"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

`EXPLAIN` 语句用于为输入语句提供逻辑/物理计划。默认情况下，此子句仅提供有关物理计划的信息。

**语法** 

```
EXPLAIN [ EXTENDED | CODEGEN | COST | FORMATTED ] statement
```

**参数**
+ **EXTENDED** 

  生成解析后的逻辑计划、分析后的逻辑计划、优化后的逻辑计划以及物理计划。

  解析后的逻辑计划是从查询中提取出的未决计划。

  分析后的逻辑计划将 `unresolvedAttribute` 和 `unresolvedRelation` 转换为完全类型化的对象。

  优化的逻辑计划通过一组优化规则进行转换，最终生成物理计划。
+ **CODEGEN** 

  生成语句的代码及物理计划（如有）。
+ **COST** 

  如果计划节点统计信息可用，则生成逻辑计划及统计信息。
+ **FORMATTED** 

  生成两大部分：物理计划概述及节点详细信息。
+ **语句** 

  指定要解释的 SQL 语句。

**示例**

```
-- Default Output
EXPLAIN select k, sum(v) from values (1, 2), (1, 3) t(k, v) group by k;
+----------------------------------------------------+
|                                                plan|
+----------------------------------------------------+
| == Physical Plan ==
*(2) HashAggregate(keys=[k#33], functions=[sum(cast(v#34 as bigint))])
+- Exchange hashpartitioning(k#33, 200), true, [id=#59]
+- *(1) HashAggregate(keys=[k#33], functions=[partial_sum(cast(v#34 as bigint))])
+- *(1) LocalTableScan [k#33, v#34]
|
+----------------------------------------------------

-- Using Extended
EXPLAIN EXTENDED select k, sum(v) from values (1, 2), (1, 3) t(k, v) group by k;
+----------------------------------------------------+
|                                                plan|
+----------------------------------------------------+
| == Parsed Logical Plan ==
'Aggregate ['k], ['k, unresolvedalias('sum('v), None)]
 +- 'SubqueryAlias `t`
+- 'UnresolvedInlineTable [k, v], [List(1, 2), List(1, 3)]
   
 == Analyzed Logical Plan ==
 k: int, sum(v): bigint
 Aggregate [k#47], [k#47, sum(cast(v#48 as bigint)) AS sum(v)#50L]
 +- SubqueryAlias `t`
    +- LocalRelation [k#47, v#48]
   
 == Optimized Logical Plan ==
 Aggregate [k#47], [k#47, sum(cast(v#48 as bigint)) AS sum(v)#50L]
 +- LocalRelation [k#47, v#48]
   
 == Physical Plan ==
 *(2) HashAggregate(keys=[k#47], functions=[sum(cast(v#48 as bigint))], output=[k#47, sum(v)#50L])
+- Exchange hashpartitioning(k#47, 200), true, [id=#79]
   +- *(1) HashAggregate(keys=[k#47], functions=[partial_sum(cast(v#48 as bigint))], output=[k#47, sum#52L])
    +- *(1) LocalTableScan [k#47, v#48]
|
+----------------------------------------------------+

-- Using Formatted
EXPLAIN FORMATTED select k, sum(v) from values (1, 2), (1, 3) t(k, v) group by k;
+----------------------------------------------------+
|                                                plan|
+----------------------------------------------------+
| == Physical Plan ==
 * HashAggregate (4)
 +- Exchange (3)
    +- * HashAggregate (2)
       +- * LocalTableScan (1)
   
   
 (1) LocalTableScan [codegen id : 1]
 Output: [k#19, v#20]
        
 (2) HashAggregate [codegen id : 1]
 Input: [k#19, v#20]
        
 (3) Exchange
 Input: [k#19, sum#24L]
        
 (4) HashAggregate [codegen id : 2]
 Input: [k#19, sum#24L]
|
+----------------------------------------------------+
```

#### LATERAL SUBQUERY 子句
<a name="supported-sql-lateral-subquery"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

`LATERAL SUBQUERY` 是前面有关键字 `LATERAL` 的子查询。该子句提供引用前置 `FROM` 子句中列的方法。如果没有 `LATERAL` 关键字，子查询只能引用外部查询中的列，而不能引用 `FROM` 子句中的列。`LATERAL SUBQUERY` 使复杂查询变得更简单、更高效。

**语法** 

```
[ LATERAL ] primary_relation [ join_relation ]
```

**参数**
+ **primary\$1relation**

  指定主要关系。它可以是下列项之一：

  1. 表关系 

  1. 别名查询 

     语法：`( query ) [ [ AS ] alias ] `

  1. 别名关系 

     `Syntax: ( relation ) [ [ AS ] alias ]` 

**示例**

```
CREATE TABLE t1 (c1 INT, c2 INT);
INSERT INTO t1 VALUES (0, 1), (1, 2);
CREATE TABLE t2 (c1 INT, c2 INT);
INSERT INTO t2 VALUES (0, 2), (0, 3);
SELECT * FROM t1,
LATERAL (SELECT * FROM t2 WHERE t1.c1 = t2.c1);
+--------+-------+--------+-------+
|  t1.c1 | t1.c2 |  t2.c1 | t2.c2 |
+-------+--------+--------+-------+
|    0   |   1   |    0   |   3   |
|    0   |   1   |    0   |   2   |
+-------+--------+--------+-------+
SELECT a, b, c FROM t1,
LATERAL (SELECT c1 + c2 AS a),
LATERAL (SELECT c1 - c2 AS b),
LATERAL (SELECT a * b AS c);
+--------+-------+--------+
|    a   |   b   |    c   |
+-------+--------+--------+
|    3   |  -1   |   -3   |
|    1   |  -1   |   -1   |
+-------+--------+--------+
```

#### LATERAL VIEW 子句
<a name="supported-sql-lateral-view"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

`LATERAL VIEW` 子句与生成器函数（例如 `EXPLODE`）结合使用，后者将生成包含一行或多行的虚拟表。`LATERAL VIEW` 将这些行应用于每个原始输出行。

**语法** 

```
LATERAL VIEW [ OUTER ] generator_function ( expression [ , ... ] ) [ table_alias ] AS column_alias [ , ... ]
```

**参数**
+ **外部**

  如果`OUTER`指定，则如果输入为空 array/map 则返回 null，或者返回 null。
+ **generator\$1function**

  指定生成器函数（`EXPLODE`、`INLINE` 等）。
+ **table\$1alias**

  `generator_function` 的别名，可选。
+ **column\$1alias**

  列出 `generator_function` 的列别名，这些别名可在输出行中使用。

  如果 `generator_function` 有多个输出列，则可以有多个别名。

**示例**

```
CREATE TABLE person (id INT, name STRING, age INT, class INT, address STRING);
INSERT INTO person VALUES
(100, 'John', 30, 1, 'Street 1'),
(200, 'Mary', NULL, 1, 'Street 2'),
(300, 'Mike', 80, 3, 'Street 3'),
(400, 'Dan', 50, 4, 'Street 4');
SELECT * FROM person
LATERAL VIEW EXPLODE(ARRAY(30, 60)) tableName AS c_age
LATERAL VIEW EXPLODE(ARRAY(40, 80)) AS d_age;
+------+-------+-------+--------+-----------+--------+--------+
|  id  | name  |  age  | class  |  address  | c_age  | d_age  |
+------+-------+-------+--------+-----------+--------+--------+
| 100  | John  | 30    | 1      | Street 1  | 30     | 40     |
| 100  | John  | 30    | 1      | Street 1  | 30     | 80     |
| 100  | John  | 30    | 1      | Street 1  | 60     | 40     |
| 100  | John  | 30    | 1      | Street 1  | 60     | 80     |
| 200  | Mary  | NULL  | 1      | Street 2  | 30     | 40     |
| 200  | Mary  | NULL  | 1      | Street 2  | 30     | 80     |
| 200  | Mary  | NULL  | 1      | Street 2  | 60     | 40     |
| 200  | Mary  | NULL  | 1      | Street 2  | 60     | 80     |
| 300  | Mike  | 80    | 3      | Street 3  | 30     | 40     |
| 300  | Mike  | 80    | 3      | Street 3  | 30     | 80     |
| 300  | Mike  | 80    | 3      | Street 3  | 60     | 40     |
| 300  | Mike  | 80    | 3      | Street 3  | 60     | 80     |
| 400  | Dan   | 50    | 4      | Street 4  | 30     | 40     |
| 400  | Dan   | 50    | 4      | Street 4  | 30     | 80     |
| 400  | Dan   | 50    | 4      | Street 4  | 60     | 40     |
| 400  | Dan   | 50    | 4      | Street 4  | 60     | 80     |
+------+-------+-------+--------+-----------+--------+--------+
SELECT c_age, COUNT(1) FROM person
LATERAL VIEW EXPLODE(ARRAY(30, 60)) AS c_age
LATERAL VIEW EXPLODE(ARRAY(40, 80)) AS d_age
GROUP BY c_age;
+--------+-----------+
| c_age  | count(1)  |
+--------+-----------+
| 60     | 8         |
| 30     | 8         |
+--------+-----------+
SELECT * FROM person
LATERAL VIEW EXPLODE(ARRAY()) tableName AS c_age;
+-----+-------+------+--------+----------+--------+
| id  | name  | age  | class  | address  | c_age  |
+-----+-------+------+--------+----------+--------+
+-----+-------+------+--------+----------+--------+
SELECT * FROM person
LATERAL VIEW OUTER EXPLODE(ARRAY()) tableName AS c_age;
+------+-------+-------+--------+-----------+--------+
|  id  | name  |  age  | class  |  address  | c_age  |
+------+-------+-------+--------+-----------+--------+
| 100  | John  | 30    | 1      | Street 1  | NULL   |
| 200  | Mary  | NULL  | 1      | Street 2  | NULL   |
| 300  | Mike  | 80    | 3      | Street 3  | NULL   |
| 400  | Dan   | 50    | 4      | Street 4  | NULL   |
+------+-------+-------+--------+-----------+--------+
```

#### LIKE 谓词
<a name="supported-sql-like-predicate"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

`LIKE` 谓词用于搜索特定模式。此谓词还支持多种模式，其量词包括 `ANY`、`SOME` 和 `ALL`。

**语法** 

```
[ NOT ] { LIKE search_pattern [ ESCAPE esc_char ] | [ RLIKE | REGEXP ] regex_pattern }
[ NOT ] { LIKE quantifiers ( search_pattern [ , ... ]) }
```

**参数**
+ **search\$1pattern**

  指定 LIKE 子句要搜索的字符串模式。可以包含特殊的模式匹配字符：
  + `%` 匹配 0 或多个字符。
  + `_` 精准匹配 1 个字符。
+ **esc\$1char**

  指定转义字符。默认的转义字符为 `\`。
+ **regex\$1pattern**

  指定要由 `RLIKE` 或 `REGEXP` 子句搜索的正则表达式搜索模式。
+ **量词** 

  指定谓词量词，包括 `ANY`、`SOME` 和 `ALL`。

  `ANY` 或 `SOME` 表示如果其中一个模式与输入匹配，则返回 true。

  `ALL` 表示如果所有模式都与输入匹配，则返回 true。

**示例**

```
CREATE TABLE person (id INT, name STRING, age INT);
INSERT INTO person VALUES
(100, 'John', 30),
(200, 'Mary', NULL),
(300, 'Mike', 80),
(400, 'Dan',  50),
(500, 'Evan_w', 16);
SELECT * FROM person WHERE name LIKE 'M%';
+---+----+----+
| id|name| age|
+---+----+----+
|300|Mike|  80|
|200|Mary|null|
+---+----+----+
SELECT * FROM person WHERE name LIKE 'M_ry';
+---+----+----+
| id|name| age|
+---+----+----+
|200|Mary|null|
+---+----+----+
SELECT * FROM person WHERE name NOT LIKE 'M_ry';
+---+------+---+
| id|  name|age|
+---+------+---+
|500|Evan_W| 16|
|300|  Mike| 80|
|100|  John| 30|
|400|   Dan| 50|
+---+------+---+
SELECT * FROM person WHERE name RLIKE 'M+';
+---+----+----+
| id|name| age|
+---+----+----+
|300|Mike|  80|
|200|Mary|null|
+---+----+----+
SELECT * FROM person WHERE name REGEXP 'M+';
+---+----+----+
| id|name| age|
+---+----+----+
|300|Mike|  80|
|200|Mary|null|
+---+----+----+
SELECT * FROM person WHERE name LIKE '%\_%';
+---+------+---+
| id|  name|age|
+---+------+---+
|500|Evan_W| 16|
+---+------+---+
SELECT * FROM person WHERE name LIKE '%$_%' ESCAPE '$';
+---+------+---+
| id|  name|age|
+---+------+---+
|500|Evan_W| 16|
+---+------+---+
SELECT * FROM person WHERE name LIKE ALL ('%an%', '%an');
+---+----+----+
| id|name| age|
+---+----+----+
|400| Dan|  50|
+---+----+----+
SELECT * FROM person WHERE name LIKE ANY ('%an%', '%an');
+---+------+---+
| id|  name|age|
+---+------+---+
|400|   Dan| 50|
|500|Evan_W| 16|
+---+------+---+
SELECT * FROM person WHERE name LIKE SOME ('%an%', '%an');
+---+------+---+
| id|  name|age|
+---+------+---+
|400|   Dan| 50|
|500|Evan_W| 16|
+---+------+---+
SELECT * FROM person WHERE name NOT LIKE ALL ('%an%', '%an');
+---+----+----+
| id|name| age|
+---+----+----+
|100|John|  30|
|200|Mary|null|
|300|Mike|  80|
+---+----+----+
SELECT * FROM person WHERE name NOT LIKE ANY ('%an%', '%an');
+---+------+----+
| id|  name| age|
+---+------+----+
|100|  John|  30|
|200|  Mary|null|
|300|  Mike|  80|
|500|Evan_W|  16|
+---+------+----+
SELECT * FROM person WHERE name NOT LIKE SOME ('%an%', '%an');
+---+------+----+
| id|  name| age|
+---+------+----+
|100|  John|  30|
|200|  Mary|null|
|300|  Mike|  80|
|500|Evan_W|  16|
+---+------+----+
```

#### OFFSET
<a name="supported-sql-offset"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

`OFFSET` 子句用于指定在开始返回 `SELECT` 语句返回的行之前需要跳过的行数。通常，该子句需与 `ORDER BY` 配合使用，以确保结果具有确定性。

**语法** 

```
OFFSET integer_expression
```

**参数**
+ **integer\$1expression**

  指定返回整数的可折叠表达式。

**示例**

```
CREATE TABLE person (name STRING, age INT);
INSERT INTO person VALUES
('Jane Doe', 25),
('Pat C', 18),
('Nikki W', 16),
('Juan L', 25),
('John D', 18),
('Jorge S', 16);

-- Skip the first two rows.
SELECT name, age FROM person ORDER BY name OFFSET 2;
+-------+---+
|   name|age|
+-------+---+
| John D| 18|
| Juan L| 25|
|Nikki W| 16|
|Jane Doe| 25|
+-------+---+

-- Skip the first two rows and returns the next three rows.
SELECT name, age FROM person ORDER BY name LIMIT 3 OFFSET 2;
+-------+---+
|   name|age|
+-------+---+
| John D| 18|
| Juan L| 25|
|Nikki W| 16|
+-------+---+

-- A function expression as an input to OFFSET.
SELECT name, age FROM person ORDER BY name OFFSET length('WAGON');
+-------+---+
|   name|age|
+-------+---+
|Jane Doe| 25|
+-------+---+
```

#### PIVOT 子句
<a name="supported-sql-pivot"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

`PIVOT` 子句用于数据透视。我们可根据特定列值获取聚合值，这些值将转换为 `SELECT` 子句中使用的多个列。`PIVOT` 子句可在表名或子查询之后指定。

**语法** 

```
PIVOT ( { aggregate_expression [ AS aggregate_expression_alias ] } [ , ... ] FOR column_list IN ( expression_list ) ) 
```

**参数** 
+ **aggregate\$1expression**

  指定聚合表达式（`(SUM(a)`、`COUNT(DISTINCT b)` 等）。
+ **aggregate\$1expression\$1alias**

  指定聚合表达式的别名。
+ **column\$1list**

  包含 `FROM` 子句中的列，该子句指定要替换为新列的列。可用方括号将各列括起来，例如 `(c1, c2)`。
+ **expression\$1list**

  指定新列，用于匹配 `column_list` 中作为聚合条件的值。您还可为这些列添加别名。

**示例**

```
CREATE TABLE person (id INT, name STRING, age INT, class INT, address STRING);
INSERT INTO person VALUES
(100, 'John', 30, 1, 'Street 1'),
(200, 'Mary', NULL, 1, 'Street 2'),
(300, 'Mike', 80, 3, 'Street 3'),
(400, 'Dan', 50, 4, 'Street 4');
SELECT * FROM person
PIVOT (
SUM(age) AS a, AVG(class) AS c
FOR name IN ('John' AS john, 'Mike' AS mike)
);
+------+-----------+---------+---------+---------+---------+
|  id  |  address  | john_a  | john_c  | mike_a  | mike_c  |
+------+-----------+---------+---------+---------+---------+
| 200  | Street 2  | NULL    | NULL    | NULL    | NULL    |
| 100  | Street 1  | 30      | 1.0     | NULL    | NULL    |
| 300  | Street 3  | NULL    | NULL    | 80      | 3.0     |
| 400  | Street 4  | NULL    | NULL    | NULL    | NULL    |
+------+-----------+---------+---------+---------+---------+
SELECT * FROM person
PIVOT (
SUM(age) AS a, AVG(class) AS c
FOR (name, age) IN (('John', 30) AS c1, ('Mike', 40) AS c2)
);
+------+-----------+-------+-------+-------+-------+
|  id  |  address  | c1_a  | c1_c  | c2_a  | c2_c  |
+------+-----------+-------+-------+-------+-------+
| 200  | Street 2  | NULL  | NULL  | NULL  | NULL  |
| 100  | Street 1  | 30    | 1.0   | NULL  | NULL  |
| 300  | Street 3  | NULL  | NULL  | NULL  | NULL  |
| 400  | Street 4  | NULL  | NULL  | NULL  | NULL  |
+------+-----------+-------+-------+-------+-------+
```

#### 集合运算符
<a name="supported-sql-set"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

集合运算符用于将两个输入关系合并为单一关系。 OpenSearch SQL 支持三种类型的集合运算符：
+ `EXCEPT` 或 `MINUS`
+ `INTERSECT` 
+ `UNION` 

输入关系必须具有相同数量的列，且各列的数据类型必须兼容。

**除了** 

`EXCEPT` 和 `EXCEPT ALL` 返回在其中一个关系中存在而在另一个中不存在的行。`EXCEPT`（或 `EXCEPT DISTINCT`）仅获取不同的行，而 `EXCEPT ALL` 不会从结果行中移除重复的行。请注意，`MINUS` 是 `EXCEPT` 的别名。

**语法** 

```
 [ ( ] relation [ ) ] EXCEPT | MINUS [ ALL | DISTINCT ] [ ( ] relation [ ) ] 
```

**示例**

```
-- Use table1 and table2 tables to demonstrate set operators in this page.
SELECT * FROM table1;
+---+
|  c|
+---+
|  3|
|  1|
|  2|
|  2|
|  3|
|  4|
+---+
SELECT * FROM table2;
+---+
|  c|
+---+
|  5|
|  1|
|  2|
|  2|
+---+
SELECT c FROM table1 EXCEPT SELECT c FROM table2;
+---+
|  c|
+---+
|  3|
|  4|
+---+
SELECT c FROM table1 MINUS SELECT c FROM table2;
+---+
|  c|
+---+
|  3|
|  4|
+---+
SELECT c FROM table1 EXCEPT ALL (SELECT c FROM table2);
+---+
|  c|
+---+
|  3|
|  3|
|  4|
+---+
SELECT c FROM table1 MINUS ALL (SELECT c FROM table2);
+---+
|  c|
+---+
|  3|
|  3|
|  4|
+---+
```

**相交** 

`INTERSECT` 和 `INTERSECT ALL` 返回同时存在于两个关系中的行。`INTERSECT`（或 `INTERSECT DISTINCT`）仅获取不同的行，而 `INTERSECT ALL` 不会从结果行中移除重复的行。

**语法** 

```
 [ ( ] relation [ ) ] INTERSECT [ ALL | DISTINCT ] [ ( ] relation [ ) ]
```

**示例**

```
(SELECT c FROM table1) INTERSECT (SELECT c FROM table2);
+---+
|  c|
+---+
|  1|
|  2|
+---+
(SELECT c FROM table1) INTERSECT DISTINCT (SELECT c FROM table2);
+---+
|  c|
+---+
|  1|
|  2|
+---+
(SELECT c FROM table1) INTERSECT ALL (SELECT c FROM table2);
+---+
|  c|
+---+
|  1|
|  2|
|  2|
+---+
```

**联盟** 

`UNION` 和 `UNION ALL` 返回在任一关系中找到的行。`UNION`（或 `UNION DISTINCT`）仅获取不同的行，而 `UNION ALL` 不会从结果行中移除重复的行。

**语法** 

```
 [ ( ] relation [ ) ] UNION [ ALL | DISTINCT ] [ ( ] relation [ ) ]
```

**示例**

```
(SELECT c FROM table1) UNION (SELECT c FROM table2);
+---+
|  c|
+---+
|  1|
|  3|
|  5|
|  4|
|  2|
+---+
(SELECT c FROM table1) UNION DISTINCT (SELECT c FROM table2);
+---+
|  c|
+---+
|  1|
|  3|
|  5|
|  4|
|  2|
+---+
SELECT c FROM table1 UNION ALL (SELECT c FROM table2);
+---+
|  c|
+---+
|  3|
|  1|
|  2|
|  2|
|  3|
|  4|
|  5|
|  1|
|  2|
|  2|
+---+
```

#### SORT BY 子句
<a name="supported-sql-sort-by"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

`SORT BY` 子句用于按用户指定的顺序返回每个分区内排序后的结果行。当存在多个分区时，`SORT BY` 可能返回部分排序的结果。这与保证输出结果完全序关系的 `ORDER BY` 子句不同。

**语法** 

```
SORT BY { expression [ sort_direction | nulls_sort_order ] [ , ... ] }
```

**参数**
+ **SORT BY**

  指定用逗号分隔的表达式列表以及用于对每个分区内行进行排序的可选参数 sort\$1direction 和 nulls\$1sort\$1order。
+ **sort\$1direction**

  （可选）指定是按升序还是降序对行进行排序。

  排序方向的有效值为 `ASC` 表示升序，`DESC` 表示降序。

  如果未明确指定排序方向，则默认按升序对行进行排序。

  语法：`[ ASC | DESC ]`
+ **nulls\$1sort\$1order**

  （可选）指定 NULL 值是在非 NULL 值之前还是之后返回。

  如果`null_sort_order`未指定，则如果 NULLs 排序顺序为，则先排序`ASC`；如果排序顺序为`DESC`，则最后排序 NULLS。

  1. 如果已指定 `NULLS FIRST`，则无论排序顺序如何，都将首先返回 NULL 值。

  2. 如果已指定 `NULLS LAST`，则无论排序顺序如何，都将最后返回 NULL 值。

  语法：`[ NULLS { FIRST | LAST } ] `

**示例**

```
CREATE TABLE person (zip_code INT, name STRING, age INT);
INSERT INTO person VALUES
(94588, 'Shirley Rodriguez', 50),
(94588, 'Juan Li', 18),
(94588, 'Anil K', 27),
(94588, 'John D', NULL),
(94511, 'David K', 42),
(94511, 'Aryan B.', 18),
(94511, 'Lalit B.', NULL);
-- Sort rows by `name` within each partition in ascending manner
SELECT name, age, zip_code FROM person SORT BY name;
+------------------+----+--------+
|              name| age|zip_code|
+------------------+----+--------+
|            Anil K|  27|   94588|
|           Juan Li|  18|   94588|
|            John D|null|   94588|
| Shirley Rodriguez|  50|   94588|
|          Aryan B.|  18|   94511|
|           David K|  42|   94511|
|          Lalit B.|null|   94511|
+------------------+----+--------+
-- Sort rows within each partition using column position.
SELECT name, age, zip_code FROM person SORT BY 1;
+----------------+----+----------+
|              name| age|zip_code|
+------------------+----+--------+
|            Anil K|  27|   94588|
|           Juan Li|  18|   94588|
|            John D|null|   94588|
| Shirley Rodriguez|  50|   94588|
|          Aryan B.|  18|   94511|
|           David K|  42|   94511|
|          Lalit B.|null|   94511|
+------------------+----+--------+

-- Sort rows within partition in ascending manner keeping null values to be last.
SELECT age, name, zip_code FROM person SORT BY age NULLS LAST;
+----+------------------+--------+
| age|              name|zip_code|
+----+------------------+--------+
|  18|           Juan Li|   94588|
|  27|            Anil K|   94588|
|  50| Shirley Rodriguez|   94588|
|null|            John D|   94588|
|  18|          Aryan B.|   94511|
|  42|           David K|   94511|
|null|          Lalit B.|   94511|
+--------------+--------+--------+

-- Sort rows by age within each partition in descending manner, which defaults to NULL LAST.
SELECT age, name, zip_code FROM person SORT BY age DESC;
+----+------------------+--------+
| age|              name|zip_code|
+----+------------------+--------+
|  50|          Shirley Rodriguez|   94588|
|  27|            Anil K|   94588|
|  18|           Juan Li|   94588|
|null|            John D|   94588|
|  42|           David K|   94511|
|  18|          Aryan B.|   94511|
|null|          Lalit B.|   94511|
+----+------------------+--------+

-- Sort rows by age within each partition in descending manner keeping null values to be first.
SELECT age, name, zip_code FROM person SORT BY age DESC NULLS FIRST;
+----+------------------+--------+
| age|              name|zip_code|
+----+------------------+--------+
|null|            John D|   94588|
|  50| Shirley Rodriguez|   94588|
|  27|            Anil K|   94588|
|  18|           Juan Li|   94588|
|null|          Lalit B.|   94511|
|  42|           David K|   94511|
|  18|          Aryan B.|   94511|
+--------------+--------+--------+

-- Sort rows within each partition based on more than one column with each column having
-- different sort direction.
SELECT name, age, zip_code FROM person
SORT BY name ASC, age DESC;
+------------------+----+--------+
|              name| age|zip_code|
+------------------+----+--------+
|            Anil K|  27|   94588|
|           Juan Li|  18|   94588|
|            John D|null|   94588|
| Shirley Rodriguez|  50|   94588|
|          Aryan B.|  18|   94511|
|           David K|  42|   94511|
|          Lalit B.|null|   94511|
+------------------+----+--------+
```

#### UNPIVOT
<a name="supported-sql-unpivot"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 SQL 命令，请参阅[支持 OpenSearch 的 SQL 命令和函数](#supported-directquery-sql)。

`UNPIVOT` 子句将多个列转换为 `SELECT` 子句中使用的多个行。`UNPIVOT` 子句可在表名或子查询之后指定。

**语法** 

```
UNPIVOT [ { INCLUDE | EXCLUDE } NULLS ] (
    { single_value_column_unpivot | multi_value_column_unpivot }
) [[AS] alias]

single_value_column_unpivot:
    values_column
    FOR name_column
    IN (unpivot_column [[AS] alias] [, ...])

multi_value_column_unpivot:
    (values_column [, ...])
    FOR name_column
    IN ((unpivot_column [, ...]) [[AS] alias] [, ...])
```

**参数**
+ **unpivot\$1column**

  包含 `FROM` 子句中的列，该子句指定我们要反转置的列。
+ **name\$1column**

  列的名称，包含反转置列的名称。
+ **values\$1column**

  列的名称，包含反转置列的值。

**示例**

```
CREATE TABLE sales_quarterly (year INT, q1 INT, q2 INT, q3 INT, q4 INT);
INSERT INTO sales_quarterly VALUES
(2020, null, 1000, 2000, 2500),
(2021, 2250, 3200, 4200, 5900),
(2022, 4200, 3100, null, null);
-- column names are used as unpivot columns
SELECT * FROM sales_quarterly
UNPIVOT (
sales FOR quarter IN (q1, q2, q3, q4)
);
+------+---------+-------+
| year | quarter | sales |
+------+---------+-------+
| 2020 | q2      | 1000  |
| 2020 | q3      | 2000  |
| 2020 | q4      | 2500  |
| 2021 | q1      | 2250  |
| 2021 | q2      | 3200  |
| 2021 | q3      | 4200  |
| 2021 | q4      | 5900  |
| 2022 | q1      | 4200  |
| 2022 | q2      | 3100  |
+------+---------+-------+
-- NULL values are excluded by default, they can be included
-- unpivot columns can be alias
-- unpivot result can be referenced via its alias
SELECT up.* FROM sales_quarterly
UNPIVOT INCLUDE NULLS (
sales FOR quarter IN (q1 AS Q1, q2 AS Q2, q3 AS Q3, q4 AS Q4)
) AS up;
+------+---------+-------+
| year | quarter | sales |
+------+---------+-------+
| 2020 | Q1      | NULL  |
| 2020 | Q2      | 1000  |
| 2020 | Q3      | 2000  |
| 2020 | Q4      | 2500  |
| 2021 | Q1      | 2250  |
| 2021 | Q2      | 3200  |
| 2021 | Q3      | 4200  |
| 2021 | Q4      | 5900  |
| 2022 | Q1      | 4200  |
| 2022 | Q2      | 3100  |
| 2022 | Q3      | NULL  |
| 2022 | Q4      | NULL  |
+------+---------+-------+
-- multiple value columns can be unpivoted per row
SELECT * FROM sales_quarterly
UNPIVOT EXCLUDE NULLS (
(first_quarter, second_quarter)
FOR half_of_the_year IN (
(q1, q2) AS H1,
(q3, q4) AS H2
)
);
+------+------------------+---------------+----------------+
|  id  | half_of_the_year | first_quarter | second_quarter |
+------+------------------+---------------+----------------+
| 2020 | H1               | NULL          | 1000           |
| 2020 | H2               | 2000          | 2500           |
| 2021 | H1               | 2250          | 3200           |
| 2021 | H2               | 4200          | 5900           |
| 2022 | H1               | 4200          | 3100           |
+------+------------------+---------------+----------------+
```

# 支持的 PPL 命令
<a name="supported-ppl"></a>

下表显示了 OpenSearch 控制面板支持哪些用于查询 CloudWatch 日志、Amazon S3 或安全湖的 PPL 命令，以及 L CloudWatch ogs Insights 支持哪些命令。 CloudWatch Logs Insights 在查询 CloudWatch 日志时使用与 OpenSearch 仪表板相同的 PPL 语法，并且这些表将两者都称为 CloudWatch 日志。

**注意**  
在 OpenSearch 服务之外分析数据时，命令的执行方式可能与对 OpenSearch 索引执行的命令不同。

**Topics**
+ [

## 命令
](#supported-ppl-commands)
+ [

## 函数
](#supported-ppl-functions)
+ [

## 为使用 OpenSearch PPL 的 CloudWatch Logs Insights 用户提供的其他信息
](#supported-ppl-for-cloudwatch-users)

## 命令
<a name="supported-ppl-commands"></a>


| PPL 命令 | 说明 | CloudWatch 日志 | Amazon S3 | 安全湖 |  命令示例 | 
| --- | --- | --- | --- | --- | --- | 
| [fields 命令](#supported-ppl-fields-command) | 显示一组需要投影的字段。 | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> fields field1, field2</pre>  | 
| [where 命令](#supported-ppl-where-command) |  根据指定的条件筛选数据。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> where field1="success"<br />| where field2 != "i -023fe0a90929d8822"<br />| fields field3, col4, col5, col6<br />| head 1000</pre>  | 
| [stats 命令](#supported-ppl-stats-command) |  执行聚合和计算。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>stats count(),<br />      count(`field1`),<br />      min(`field1`),<br />      max(`field1`),<br />      avg(`field1`)<br />by field2<br />| head 1000</pre>  | 
| [parse 命令](#supported-ppl-parse-command) |  从字符串中提取正则表达式（regex）模式，并显示提取出的模式。提取出的模式可进一步用于创建新字段或筛选数据。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>parse `field1` ".*/(?<field2>[^/]+$)"<br />| where field2 = "requestId"<br />| fields field2, `field2`<br />| head 1000</pre>  | 
| [patterns 命令](#supported-ppl-patterns-command) |  从文本字段中提取日志模式，并将结果附加到搜索结果中。按日志模式进行分组，便于从海量日志数据中聚合统计信息，从而进行分析和故障排查。  | 不支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/negative_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>patterns new_field='no_numbers' pattern='[0-9]' message<br />| fields message, no_numbers</pre>  | 
| [sort 命令](#supported-ppl-sort-command) |  按字段名称对显示的结果进行排序。使用 **sor *FieldName*t-** 按降序排序。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>stats count(),<br />      count(`field1`),<br />      min(`field1`) as field1Alias,<br />      max(`field1`),<br />      avg(`field1`)<br />by field2<br />| sort -field1Alias<br />| head 1000</pre>  | 
| [eval 命令](#supported-ppl-eval-command) |  修改或处理字段的值，并将其存储在不同的字段中。这有助于对列进行数学修改、对列应用字符串函数或对列应用日期函数。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>eval field2 = `field1` * 2<br />| fields field1, field2<br />| head 20</pre>  | 
| [rename 命令](#supported-ppl-rename-command) |  重命名搜索结果中的一个或多个字段。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>rename field2 as field1<br />| fields field1</pre>  | 
| [head 命令](#supported-ppl-head-command) |  将显示的查询结果限制为前 N 行。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> fields `@message`<br />| head 20</pre>  | 
| [grok 命令](#supported-ppl-grok-command) |  使用基于正则表达式的 grok 模式解析文本字段，并将结果附加到搜索结果中。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> grok email '.+@%{HOSTNAME:host}'<br />| fields email</pre>  | 
| [top 命令](#supported-ppl-top-command) |  查找字段中最频繁出现的值。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> top 2 Field1 by Field2</pre>  | 
| [dedup 命令](#supported-ppl-dedup-command) |  根据指定的字段删除重复的条目。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>dedup field1<br />| fields field1, field2, field3</pre>  | 
| [join 命令](#supported-ppl-join-commands) |  将两个数据集联接在一起。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>source=customer<br />| join ON c_custkey = o_custkey orders<br />| head 10</pre>  | 
| [lookup 命令](#supported-ppl-lookup-commands) |  通过添加或替换查询索引（维度表）中的数据，丰富搜索数据。可使用维度表中的值扩展索引的字段，在匹配查找条件时追加或替换值  | 不支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/negative_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>where orderType = 'Cancelled'<br />| lookup account_list, mkt_id AS mkt_code<br />  replace amount, account_name as name<br />| stats count(mkt_code), avg(amount)<br />  by name</pre>  | 
| [subquery 命令](#supported-ppl-subquery-commands) | 在管道处理语言（PPL）语句中执行复杂的嵌套查询。 | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>where id in [<br />  subquery source=users<br />  | where user in [<br />    subquery source=actions<br />    | where action="login"<br />    | fields user<br />  ]<br />  | fields uid<br />]</pre>  | 
| [rare 命令](#supported-ppl-rare-command) |  查找字段列表中所有字段中出现频率最低的值。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> rare Field1 by Field2</pre>  | 
| [trendline 命令](#supported-ppl-trendline-commands) | 计算字段的移动平均值。 | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> trendline sma(2, field1) as field1Alias</pre>  | 
| [eventstats 命令](#supported-ppl-eventstats-command) | 使用计算得出的汇总统计数据丰富事件数据。它会分析您事件中的指定字段，计算各种统计指标，然后将这些结果作为新字段附加到每个原始事件上。 |  支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg)（`count()` 除外）  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> eventstats sum(field1) by field2</pre>  | 
| [flatten 命令](#supported-ppl-flatten-command) |  展平字段，该字段必须是以下类型：`struct<?,?> or array<struct<?,?>>`  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> source=table | flatten field1</pre>  | 
| [字段摘要](#supported-ppl-field-summary-command) | 计算每个字段的基本统计数据（计数、非重复计数、最小值、最大值、平均值、标准差和平均值）。 | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg)（每个查询一个字段） | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>where field1 != 200<br />| fieldsummary includefields=field1 nulls=true</pre>  | 
| [fillnull 命令](#supported-ppl-fillnull-command) | 使用您提供的值填充 null 字段。可在一个或多个字段中使用。 | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>fields field1<br />| eval field2=field1<br />| fillnull value=0 field1</pre>  | 
| [expand 命令](#supported-ppl-expand-command) | 将包含多个值的字段拆分为单独的行，为指定字段中的每个值创建新行。 | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>expand employee<br />| stats max(salary) as max<br />  by state, company</pre>  | 
| [describe 命令](#supported-ppl-describe-command) |  获取有关表、模式和目录的结构以及元数据的详细信息  | 不支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/negative_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre> describe schema.table</pre>  | 

## 函数
<a name="supported-ppl-functions"></a>


| PPL 函数 | 说明 | CloudWatch 日志 | Amazon S3 | 安全湖 |  命令示例 | 
| --- | --- | --- | --- | --- | --- | 
|  [PPL 字符串函数](#supported-ppl-string-functions) (`CONCAT`, `CONCAT_WS`, `LENGTH`, `LOWER`, `LTRIM`, `POSITION`, `REVERSE`, `RIGHT`, `RTRIM`, `SUBSTRING`, `TRIM`, `UPPER`)  |  PPL 中的内置函数，可在 PPL 查询中操作和转换字符串及文本数据。例如，转换大小写、合并字符串、提取部分内容以及清理文本。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>eval col1Len = LENGTH(col1)<br />| fields col1Len</pre>  | 
|  [PPL 日期和时间函数](#supported-ppl-date-time-functions) (`DAY`, `DAYOFMONTH`, `DAY_OF_MONTH`,`DAYOFWEEK`, `DAY_OF_WEEK`, `DAYOFYEAR`, `DAY_OF_YEAR`, `DAYNAME`, `FROM_UNIXTIME`, `HOUR`, `HOUR_OF_DAY`, `LAST_DAY`, `LOCALTIMESTAMP`, `LOCALTIME`, `MAKE_DATE`, `MINUTE`, `MINUTE_OF_HOUR`, `MONTH`, `MONTHNAME`, `MONTH_OF_YEAR`, `NOW`, `QUARTER`, `SECOND`, `SECOND_OF_MINUTE`, `SUBDATE`, `SYSDATE`, `TIMESTAMP`, `UNIX_TIMESTAMP`, `WEEK`, `WEEKDAY`, `WEEK_OF_YEAR`, `DATE_ADD`, `DATE_SUB`, `TIMESTAMPADD`, `TIMESTAMPDIFF`, `UTC_TIMESTAMP`, `CURRENT_TIMEZONE`)  |  内置函数，用于处理和转换 PPL 查询中的日期和时间戳数据。例如，**date\$1add**、**date\$1format**、**datediff** 和 **current\$1date**。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>eval newDate = ADDDATE(DATE('2020-08-26'), 1)<br />| fields newDate</pre>  | 
|  [PPL 条件函数](#supported-ppl-condition-functions) (`EXISTS`, `IF`, `IFNULL`, `ISNOTNULL`, `ISNULL`, `NULLIF`)  |  内置函数，可对多行数据执行计算以生成单个汇总值。例如，**sum**、**count**、**avg**、**max** 和 **min**。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>eval field2 = isnull(col1)<br />| fields field2, col1, field3  </pre>  | 
|  [PPL 数学函数](#supported-ppl-math-functions) (`ABS`, `ACOS`, `ASIN`, `ATAN`, `ATAN2`, `CEIL`, `CEILING`, `CONV`, `COS`, `COT`, `CRC32`, `DEGREES`, `E`, `EXP`, `FLOOR`, `LN`, `LOG`, `LOG2`, `LOG10`, `MOD`, `PI`. `POW`, `POWER`, `RADIANS`, `RAND`, `ROUND`, `SIGN`, `SIN`, `SQRT`, `CBRT`)  |  内置函数，用于在 PPL 查询中执行数学计算和转换。例如：**abs**（绝对值）、**round**（四舍五入）、**sqrt**（平方根）、**pow**（乘方计算）和 **ceil**（向上取整到最接近的整数）。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>eval field2 = ACOS(col1)<br />| fields col1</pre>  | 
|  [PPL 表达式](#supported-ppl-expressions) （算术运算符（`+`、`-`、`*`）；谓词运算符（`>. <`、`IN)`））  |  表达式（尤其是值表达式）的内置函数，返回标量值。表达式具有不同的类型和形式。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>where age > (25 + 5)<br />| fields age  </pre>  | 
|  [PPL IP 地址函数](#supported-ppl-ip-address-functions) (`CIDRMATCH`)  |  用于处理 IP 地址的内置函数，例如 CIDR。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>where cidrmatch(ip, '***********/24')<br />| fields ip </pre>  | 
|  [PPL JSON 函数](#supported-ppl-json-functions) (`ARRAY_LENGTH`, `ARRAY_LENGTH`, `JSON`, `JSON_ARRAY`, `JSON_EXTRACT`, `JSON_KEYS`, `JSON_OBJECT`, `JSON_VALID`, `TO_JSON_STRING`)  |  用于处理 JSON 的内置函数，包括数组、提取及验证。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>eval `json_extract('{"a":"b"}', '$.a')` = json_extract('{"a":"b"}', '$a')</pre>  | 
|  [PPL Lambda 函数](#supported-ppl-lambda-functions) (`EXISTS`, `FILTER`, `REDUCE`, `TRANSFORM`)  |  用于处理 JSON 的内置函数，包括数组、提取及验证。  | 不支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/negative_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>eval array = json_array(1, -1, 2),<br />     result = filter(array, x -> x > 0)<br />| fields result</pre>  | 
|  [PPL 加密哈希函数](#supported-ppl-cryptographic-functions) (`MD5`, `SHA1`, `SHA2`)  |  内置函数，可生成数据的唯一指纹，这些指纹可用于验证、比较或作为更复杂安全协议的一部分。  | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) | 支持 ![\[alt text not found\]](http://docs.aws.amazon.com/zh_cn/opensearch-service/latest/developerguide/images/success_icon.svg) |  <pre>eval `MD5('hello')` = MD5('hello')<br />| fields `MD5('hello')`</pre>  | 

## 为使用 OpenSearch PPL 的 CloudWatch Logs Insights 用户提供的其他信息
<a name="supported-ppl-for-cloudwatch-users"></a>

尽管 CloudWatch Logs Insights 支持大多数 OpenSearch PPL 命令和功能，但目前不支持某些命令和功能。例如，目前不支持 PPL 中的 Lookup 命令。自 2025 年 6 月 2 日起，L CloudWatch ogs Insights 现在支持 PPL 中的 JOIN、子查询、Flatten、Fillnull、Expand、Cidrmatch 和 JSON 函数。有关支持的查询命令和函数的完整列表，请参阅上表中的 Ama CloudWatch zon Logs 列。

### 示例查询和限额
<a name="sample-queries"></a>

以下内容适用于 CloudWatch Logs Insights OpenSearch 用户和查询 CloudWatch 数据的用户。

有关查询 OpenSearch 服务 CloudWatch 日志时适用的限制的信息，请参阅 Amazon Logs 用户指南中的[CloudWatch CloudWatch 日志配额](https://docs.aws.amazon.com/AmazonCloudWatch/latest/logs/cloudwatch_limits_cwl.html)。限制包括您可以查询的 CloudWatch 日志组数量、可以执行的最大并发查询数、最长查询执行时间以及结果中返回的最大行数。无论您使用哪种语言查询 CloudWatch 日志（即 OpenSearch PPL、SQL 和 Logs Insights QL），限制都是一样的。

### DDL 命令
<a name="supported-ppl-commands-details"></a>

**Topics**
+ [

#### comment
](#supported-ppl-comment)
+ [

#### 关联命令
](#supported-ppl-correlation-commands)
+ [

#### dedup 命令
](#supported-ppl-dedup-command)
+ [

#### describe 命令
](#supported-ppl-describe-command)
+ [

#### eval 命令
](#supported-ppl-eval-command)
+ [

#### eventstats 命令
](#supported-ppl-eventstats-command)
+ [

#### expand 命令
](#supported-ppl-expand-commands)
+ [

#### explain 命令
](#supported-ppl-explain-command)
+ [

#### fillnull 命令
](#supported-ppl-fillnull-command)
+ [

#### fields 命令
](#supported-ppl-fields-command)
+ [

#### flatten 命令
](#supported-ppl-flatten-command)
+ [

#### grok 命令
](#supported-ppl-grok-command)
+ [

#### head 命令
](#supported-ppl-head-command)
+ [

#### join 命令
](#supported-ppl-join-commands)
+ [

#### lookup 命令
](#supported-ppl-lookup-commands)
+ [

#### parse 命令
](#supported-ppl-parse-command)
+ [

#### patterns 命令
](#supported-ppl-patterns-command)
+ [

#### rare 命令
](#supported-ppl-rare-command)
+ [

#### rename 命令
](#supported-ppl-rename-command)
+ [

#### search 命令
](#supported-ppl-search-command)
+ [

#### sort 命令
](#supported-ppl-sort-command)
+ [

#### stats 命令
](#supported-ppl-stats-command)
+ [

#### subquery 命令
](#supported-ppl-subquery-commands)
+ [

#### top 命令
](#supported-ppl-top-command)
+ [

#### trendline 命令
](#supported-ppl-trendline-commands)
+ [

#### where 命令
](#supported-ppl-where-command)
+ [

#### 字段摘要
](#supported-ppl-field-summary-command)
+ [

#### expand 命令
](#supported-ppl-expand-command)
+ [

#### PPL 函数
](#supported-ppl-functions-details)

#### comment
<a name="supported-ppl-comment"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

PPL 同时支持行注释和块注释。系统不会评估注释文本。

**行注释**  
行注释以两个斜线 // 开头，以换行结束。

示例：

```
os> source=accounts | top gender // finds most common gender of all the accounts
fetched rows / total rows = 2/2
+----------+
| gender   |
|----------|
| M        |
| F        |
+----------+
```

**块注释**  
块注释以斜杠后跟星号 \$1\$1 开头，以星号后跟斜杠 \$1/ 结束。

示例：

```
os> source=accounts | dedup 2 gender /* dedup the document with gender field keep 2 duplication */ | fields account_number, gender
fetched rows / total rows = 3/3
+------------------+----------+
| account_number   | gender   |
|------------------+----------|
| 1                | M        |
| 6                | M        |
| 13               | F        |
+------------------+----------+
```

#### 关联命令
<a name="supported-ppl-correlation-commands"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

您可以根据共同的维度和时间范围关联不同的数据来源。

当处理来自不同垂直领域的大量数据时，这种关联至关重要。这些数据虽共享相同时间段，却未经过正式同步。

通过根据时间范围和相似维度关联这些不同的数据来源，您可以丰富数据并挖掘有价值的见解。

**示例**  
可观测性域包含三个不同的数据来源：
+ 日志
+ 指标
+ 跟踪

这些数据来源可能共享共同的维度。要从一个数据来源过渡到另一个数据来源，您需要进行正确的关联。使用语义命名规范，可识别日志、跟踪和指标中的共享元素。

示例：

```
{
  "@timestamp": "2018-07-02T22:23:00.186Z",
  "aws": {
    "elb": {
      "backend": {
        "http": {
          "response": {
            "status_code": 500
          }
        },
        "ip": "********",
        "port": "80"
      },
      ...
     "target_port": [
        "10.0.0.1:80"
      ],
      "target_status_code": [
        "500"
      ],
      "traceId": "Root=1-58337262-36d228ad5d99923122bbe354",
      "type": "http"
    }
  },
  "cloud": {
    "provider": "aws"
  },
  "http": {
    "request": {
    ...
  },
  "communication": {
    "source": {
      "address": "**************",
      "ip": "**************",
      "port": 2817
    }
  },
  "traceId": "Root=1-58337262-36d228ad5d99923122bbe354"
}
```

此示例显示了来自驻留在其上的 AWS服务的 AWS ELB 日志。此示例显示状态码为 500 的后端 HTTP 响应，表示存在错误。这可能触发警报，也可能成为常规监控过程的一部分。下一步是收集有关此事件的相关数据，以便开展全面调查。

虽然您可能想查询与时间范围相关的所有数据，但这种方法可能令人不堪重负。您最终可能面临信息过载的困境，耗费更多时间筛选无关数据，反而难以找出根本原因。

相反，您可采用更具针对性的方法，通过关联不同数据来源的信息以实现目标。可使用以下维度实现关联：
+ **IP**：`"ip": "10.0.0.1" | "ip": "**************"`
+ **端口**：`"port": 2817 | "target_port": "10.0.0.1:80"`

假设您能够访问其他跟踪和指标索引，并且熟悉模式结构，则可以创建更精确的关联查询。

以下是可能需要进行关联处理的跟踪索引文档示例，其中包含 HTTP 信息：

```
{
  "traceId": "c1d985bd02e1dbb85b444011f19a1ecc",
  "spanId": "55a698828fe06a42",
  "traceState": [],
  "parentSpanId": "",
  "name": "mysql",
  "kind": "CLIENT",
  "@timestamp": "2021-11-13T20:20:39+00:00",
  "events": [
    {
      "@timestamp": "2021-03-25T17:21:03+00:00",
       ...
    }
  ],
  "links": [
    {
      "traceId": "c1d985bd02e1dbb85b444011f19a1ecc",
      "spanId": "55a698828fe06a42w2",
      },
      "droppedAttributesCount": 0
    }
  ],
  "resource": {
    "service@name": "database",
    "telemetry@sdk@name": "opentelemetry",
    "host@hostname": "ip-172-31-10-8.us-west-2.compute.internal"
  },
  "status": {
    ...
  },
  "attributes": {
    "http": {
      "user_agent": {
        "original": "Mozilla/5.0"
      },
      "network": {
         ...
        }
      },
      "request": {
         ...
        }
      },
      "response": {
        "status_code": "200",
        "body": {
          "size": 500
        }
      },
      "client": {
        "server": {
          "socket": {
            "address": "***********",
            "domain": "example.com",
            "port": 80
          },
          "address": "***********",
          "port": 80
        },
        "resend_count": 0,
        "url": {
          "full": "http://example.com"
        }
      },
      "server": {
        "route": "/index",
        "address": "***********",
        "port": 8080,
        "socket": {
         ...
        },
        "client": {
         ...
         }
        },
        "url": {
         ...
        }
      }
    }
  }
}
```

通过这种方法，你可以看到可以与 elb 日志关联 client/server `ip`的 http，从而更好地了解系统的行为和状况。`traceId`

**新的关联查询命令**  
以下是允许此类调查的新命令：

```
source alb_logs, traces | where alb_logs.ip="10.0.0.1" AND alb_logs.cloud.provider="aws"| 
correlate exact fields(traceId, ip) scope(@timestamp, 1D) mapping(alb_logs.ip = traces.attributes.http.server.address, alb_logs.traceId = traces.traceId )
```

以下是命令中各部分的功能说明：

1. `source alb_logs, traces`：这用于选择要关联的数据来源。

1. `where ip="10.0.0.1" AND cloud.provider="aws"`：这用于缩小搜索范围。

1. `correlate exact fields(traceId, ip)`：这指示系统根据下列字段的精确匹配关联数据：
   + `ip` 字段具有显式筛选条件，因此可用于所有数据来源的关联。
   + `traceId` 字段没有显式筛选条件，因此可用于匹配所有数据来源中相同的 traceId。

字段名称表明该函数在关联命令中的逻辑含义。实际的联接条件取决于您提供的映射语句。

术语 `exact` 表示关联语句要求所有字段完全匹配才能完成查询语句。

术语 `approximate` 将尝试在最佳情况下进行匹配，且不会拒绝包含部分匹配的行。

**处理不同的字段映射**  
如果同一逻辑字段（例如 `ip`）在不同数据来源中具有不同的名称，则需要提供路径字段的显式映射关系。为解决此问题，您可以扩展关联条件，使不同字段名称在逻辑含义相近时也能匹配。具体操作方法如下：

```
alb_logs.ip = traces.attributes.http.server.address, alb_logs.traceId = traces.traceId    
```

对于参与关联联接的每个字段，都应提供相关的映射语句，其中包括要通过此关联命令进行连接的所有表。

**示例**  
在此示例中，有 2 个来源：`alb_logs, traces`

有 2 个字段：`traceId, ip`

有 2 个映射语句：`alb_logs.ip = traces.attributes.http.server.address, alb_logs.traceId = traces.traceId`

**确定相关时间范围**  
要简化执行引擎（驱动程序）的工作，可以添加 scope 语句。这明确指示联接查询应在此搜索的时间范围内进行。

`scope(@timestamp, 1D)` i

在此示例中，搜索范围以每日为基准，因此同一天出现的关联会归为一组。此范围限定机制可简化操作并提升结果控制精度，支持根据需求进行增量检索解析。

**支持驱动程序**  
新的关联命令实际上是 'hidden' 联接命令。因此，仅以下 PPL 驱动程序支持此命令。在这些驱动程序中，关联命令将直接转换为相应的 Catalyst Join 逻辑计划。

**示例**  
`source alb_logs, traces, metrics | where ip="10.0.0.1" AND cloud.provider="aws"| correlate exact on (ip, port) scope(@timestamp, 2018-07-02T22:23:00, 1 D)`

**逻辑计划：**

```
'Project [*]
+- 'Join Inner, ('ip && 'port)
   :- 'Filter (('ip === "10.0.0.1" & 'cloud.provider === "aws") & inTimeScope('@timestamp, "2018-07-02T22:23:00", "1 D"))
      +- 'UnresolvedRelation [alb_logs]
   +- 'Join Inner, ('ip & 'port)
      :- 'Filter (('ip === "10.0.0.1" & 'cloud.provider === "aws") & inTimeScope('@timestamp, "2018-07-02T22:23:00", "1 D"))
         +- 'UnresolvedRelation [traces]
      +- 'Filter (('ip === "10.0.0.1" & 'cloud.provider === "aws") & inTimeScope('@timestamp, "2018-07-02T22:23:00", "1 D"))
         +- 'UnresolvedRelation [metrics]
```

催化引擎根据最高效的联接顺序优化此查询。

#### dedup 命令
<a name="supported-ppl-dedup-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

使用 `dedup` 命令，根据指定字段从搜索结果中移除重复文档。

**语法**  
使用以下语法：

```
dedup [int] <field-list> [keepempty=<bool>] [consecutive=<bool>] 
```

**`int`**
+ 可选。
+ 当指定 <int> 时，`dedup` 命令会为每个组合保留多个事件。<int> 的数字必须大于 0。如果未指定数字，则仅保留第一个出现的事件。所有其他重复项均从结果中移除。
+ 默认：1

**`keepempty`**
+ 可选。
+ 如果为 true，则保留字段列表中任何字段值为 NULL 或 MISSING 的文档。
+ 默认：false

**`consecutive`**
+ 可选。
+ 如果为 true，则仅移除具有连续重复值组合的事件。
+ 默认：false

**`field-list`**
+ 必需。
+ 以逗号分隔的字段列表。至少需要填写一个字段。

**示例 1：按单一字段去重**  
该示例说明如何使用性别字段对文档进行去重处理。

PPL 查询：

```
os> source=accounts | dedup gender | fields account_number, gender;
fetched rows / total rows = 2/2
+------------------+----------+
| account_number   | gender   |
|------------------+----------|
| 1                | M        |
| 13               | F        |
+------------------+----------+
```

**示例 2：保留 2 份重复文档**  
该示例说明如何使用性别字段对文档进行去重处理，同时保留两份重复文档。

PPL 查询：

```
os> source=accounts | dedup 2 gender | fields account_number, gender;
fetched rows / total rows = 3/3
+------------------+----------+
| account_number   | gender   |
|------------------+----------|
| 1                | M        |
| 6                | M        |
| 13               | F        |
+------------------+----------+
```

**示例 3：默认保留或忽略空字段**  
该示例说明如何通过保留 null 值字段对文档进行去重处理。

PPL 查询：

```
os> source=accounts | dedup email keepempty=true | fields account_number, email;
fetched rows / total rows = 4/4
+------------------+-----------------------+
| account_number   | email                 |
+------------------+-----------------------+
| 1                | john_doe@example.com  |
| 6                | jane_doe@example.com  |
| 13               | null                  |
| 18               | juan_li@example.com   |
+------------------+-----------------------+
```

该示例说明如何通过忽略空值字段对文档进行去重处理。

PPL 查询：

```
os> source=accounts | dedup email | fields account_number, email;
fetched rows / total rows = 3/3
+------------------+-----------------------+
| account_number   | email                 |
+------------------+-----------------------+
| 1                | john_doe@example.com  |
| 6                | jane_doe@example.com  |
| 18               | juan_li@example.com   |
+------------------+-----------------------+
```

**示例 4：连续文档中的去重**  
该示例说明如何在连续文档中进行去重处理。

PPL 查询：

```
os> source=accounts | dedup gender consecutive=true | fields account_number, gender;
fetched rows / total rows = 3/3
+------------------+----------+
| account_number   | gender   |
+------------------+----------+
| 1                | M        |
| 13               | F        |
| 18               | M        |
+------------------+----------+
```

**其他示例**
+ `source = table | dedup a | fields a,b,c`
+ `source = table | dedup a,b | fields a,b,c`
+ `source = table | dedup a keepempty=true | fields a,b,c`
+ `source = table | dedup a,b keepempty=true | fields a,b,c`
+ `source = table | dedup 1 a | fields a,b,c`
+ `source = table | dedup 1 a,b | fields a,b,c`
+ `source = table | dedup 1 a keepempty=true | fields a,b,c`
+ `source = table | dedup 1 a,b keepempty=true | fields a,b,c`
+ `source = table | dedup 2 a | fields a,b,c`
+ `source = table | dedup 2 a,b | fields a,b,c`
+ `source = table | dedup 2 a keepempty=true | fields a,b,c`
+ `source = table | dedup 2 a,b keepempty=true | fields a,b,c`
+ `source = table | dedup 1 a consecutive=true| fields a,b,c`（不支持连续去重处理）

**限制**
+ 对于 `| dedup 2 a, b keepempty=false`

  ```
  DataFrameDropColumns('_row_number_)
  +- Filter ('_row_number_ <= 2) // allowed duplication = 2
     +- Window [row_number() windowspecdefinition('a, 'b, 'a ASC NULLS FIRST, 'b ASC NULLS FIRST, specifiedwindowframe(RowFrame, unboundedpreceding$(), currentrow$())) AS _row_number_], ['a, 'b], ['a ASC NULLS FIRST, 'b ASC NULLS FIRST]
         +- Filter (isnotnull('a) AND isnotnull('b)) // keepempty=false
            +- Project
               +- UnresolvedRelation
  ```
+ 对于 `| dedup 2 a, b keepempty=true`

  ```
  Union
  :- DataFrameDropColumns('_row_number_)
  :  +- Filter ('_row_number_ <= 2)
  :     +- Window [row_number() windowspecdefinition('a, 'b, 'a ASC NULLS FIRST, 'b ASC NULLS FIRST, specifiedwindowframe(RowFrame, unboundedpreceding$(), currentrow$())) AS _row_number_], ['a, 'b], ['a ASC NULLS FIRST, 'b ASC NULLS FIRST]
  :        +- Filter (isnotnull('a) AND isnotnull('b))
  :           +- Project
  :              +- UnresolvedRelation
  +- Filter (isnull('a) OR isnull('b))
     +- Project
        +- UnresolvedRelation
  ```

#### describe 命令
<a name="supported-ppl-describe-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

使用 `describe` 命令，获取有关表、模式和目录的结构以及元数据的详细信息。以下是 `describe` 命令的不同示例和使用案例。

**描述**
+ `describe table` 此命令等同于 `DESCRIBE EXTENDED table` SQL 命令
+ `describe schema.table`
+ `describe schema.`table``
+ `describe catalog.schema.table`
+ `describe catalog.schema.`table``
+ `describe `catalog`.`schema`.`table``

#### eval 命令
<a name="supported-ppl-eval-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

`eval` 命令计算表达式，并将结果附加到搜索结果中。

**语法**  
使用以下语法：

```
eval <field>=<expression> ["," <field>=<expression> ]...    
```
+ `field`：必需。如果字段名称不存在，则会添加新的字段。如果已存在字段名称，则会进行覆盖。
+  `expression`：必需。系统支持的任何表达式。

**示例 1：创建新字段**  
此示例说明如何为每个文档创建新 `doubleAge` 字段。新的 `doubleAge` 是年龄乘以 2 的评估结果。

PPL 查询：

```
os> source=accounts | eval doubleAge = age * 2 | fields age, doubleAge ;
fetched rows / total rows = 4/4
+-------+-------------+
| age   | doubleAge   |
|-------+-------------|
| 32    | 64          |
| 36    | 72          |
| 28    | 56          |
| 33    | 66          |
+-------+-------------+
```

**示例 2：覆盖现有字段**  
此示例说明如何使用当前年龄加 1 覆盖年龄字段。

PPL 查询：

```
os> source=accounts | eval age = age + 1 | fields age ;
fetched rows / total rows = 4/4
+-------+
| age   |
|-------|
| 33    |
| 37    |
| 29    |
| 34    |
+-------+
```

**示例 3：使用在 eval 中定义的字段创建新字段**  
此示例说明如何使用在 eval 命令中定义的字段创建新 `ddAge` 字段。新字段 `ddAge` 是 `doubleAge` 乘以 2 的计算结果，其中 `doubleAge` 在 eval 命令中进行定义。

PPL 查询：

```
os> source=accounts | eval doubleAge = age * 2, ddAge = doubleAge * 2 | fields age, doubleAge, ddAge ;
fetched rows / total rows = 4/4
+-------+-------------+---------+
| age   | doubleAge   | ddAge   |
|-------+-------------+---------|
| 32    | 64          | 128     |
| 36    | 72          | 144     |
| 28    | 56          | 112     |
| 33    | 66          | 132     |
+-------+-------------+---------+
```

假设：`a`、`b`、`c` 是 `table` 中的现有存在字段

**其他示例**
+ `source = table | eval f = 1 | fields a,b,c,f`
+ `source = table | eval f = 1`（输出 a、b、c、f 字段）
+ `source = table | eval n = now() | eval t = unix_timestamp(a) | fields n,t`
+ `source = table | eval f = a | where f > 1 | sort f | fields a,b,c | head 5`
+ `source = table | eval f = a * 2 | eval h = f * 2 | fields a,f,h`
+ `source = table | eval f = a * 2, h = f * 2 | fields a,f,h`
+ `source = table | eval f = a * 2, h = b | stats avg(f) by h`
+ `source = table | eval f = ispresent(a)`
+ `source = table | eval r = coalesce(a, b, c) | fields r`
+ `source = table | eval e = isempty(a) | fields e`
+ `source = table | eval e = isblank(a) | fields e`
+ `source = table | eval f = case(a = 0, 'zero', a = 1, 'one', a = 2, 'two', a = 3, 'three', a = 4, 'four', a = 5, 'five', a = 6, 'six', a = 7, 'se7en', a = 8, 'eight', a = 9, 'nine')`
+ `source = table | eval f = case(a = 0, 'zero', a = 1, 'one' else 'unknown')`
+ `source = table | eval f = case(a = 0, 'zero', a = 1, 'one' else concat(a, ' is an incorrect binary digit'))`
+ `source = table | eval f = a in ('foo', 'bar') | fields f`
+ `source = table | eval f = a not in ('foo', 'bar') | fields f`

**使用案例示例进行评估：**  


```
source = table | eval e = eval status_category =
case(a >= 200 AND a < 300, 'Success',
a >= 300 AND a < 400, 'Redirection',
a >= 400 AND a < 500, 'Client Error',
a >= 500, 'Server Error'
else 'Unknown')
```

**使用其他案例示例进行评估：**  


假设：`a`、`b`、`c` 是 `table` 中的现有存在字段

**其他示例**
+ `source = table | eval f = 1 | fields a,b,c,f`
+ `source = table | eval f = 1`（输出 a、b、c、f 字段）
+ `source = table | eval n = now() | eval t = unix_timestamp(a) | fields n,t`
+ `source = table | eval f = a | where f > 1 | sort f | fields a,b,c | head 5`
+ `source = table | eval f = a * 2 | eval h = f * 2 | fields a,f,h`
+ `source = table | eval f = a * 2, h = f * 2 | fields a,f,h`
+ `source = table | eval f = a * 2, h = b | stats avg(f) by h`
+ `source = table | eval f = ispresent(a)`
+ `source = table | eval r = coalesce(a, b, c) | fields r`
+ `source = table | eval e = isempty(a) | fields e`
+ `source = table | eval e = isblank(a) | fields e`
+ `source = table | eval f = case(a = 0, 'zero', a = 1, 'one', a = 2, 'two', a = 3, 'three', a = 4, 'four', a = 5, 'five', a = 6, 'six', a = 7, 'se7en', a = 8, 'eight', a = 9, 'nine')`
+ `source = table | eval f = case(a = 0, 'zero', a = 1, 'one' else 'unknown')`
+ `source = table | eval f = case(a = 0, 'zero', a = 1, 'one' else concat(a, ' is an incorrect binary digit'))`
+ `source = table | eval f = a in ('foo', 'bar') | fields f`
+ `source = table | eval f = a not in ('foo', 'bar') | fields f`

**使用案例示例进行评估：**  


```
source = table | eval e = eval status_category =
case(a >= 200 AND a < 300, 'Success',
a >= 300 AND a < 400, 'Redirection',
a >= 400 AND a < 500, 'Client Error',
a >= 500, 'Server Error'
else 'Unknown')
```

**使用其他案例示例进行评估：**  


```
source = table |  where ispresent(a) |
eval status_category =
 case(a >= 200 AND a < 300, 'Success',
  a >= 300 AND a < 400, 'Redirection',
  a >= 400 AND a < 500, 'Client Error',
  a >= 500, 'Server Error'
  else 'Incorrect HTTP status code'
 )
 | stats count() by status_category
```

**限制**
+ 不支持覆盖现有字段。尝试这样做的查询将抛出异常，并显示消息 "Reference 'a' is ambiguous"。

  ```
  - `source = table | eval a = 10 | fields a,b,c`
  - `source = table | eval a = a * 2 | stats avg(a)`
  - `source = table | eval a = abs(a) | where a > 0`
  - `source = table | eval a = signum(a) | where a < 0`
  ```

#### eventstats 命令
<a name="supported-ppl-eventstats-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

使用 `eventstats` 命令，通过计算得出的汇总统计数据丰富事件数据。该功能通过分析事件中的指定字段，计算各种统计指标，并将这些结果作为新字段附加到每个原始事件中。

**eventstats 的关键方面**

1. 可在整个结果集或定义的组内执行计算。

1. 原始事件保持不变，新增字段用于存储统计结果。

1. 该命令特别适用于比较分析、识别异常值或为单个事件提供额外背景信息。

**stats 和 eventstats 之间的区别**  
`stats` 和 `eventstats` 命令均用于计算统计数据，但在操作方式和输出结果方面存在关键差异。

**输出格式**
+ `stats`：生成仅包含计算统计数据的汇总表。
+ `eventstats`：将计算出的统计数据作为新字段添加到现有事件中，同时保留原始数据。

**事件保留**
+ `stats`：将结果集简化为仅包含统计摘要，舍弃单个事件。
+ `eventstats`：保留所有原始事件，并添加包含计算统计数据的新字段。

**使用案例**
+ `stats`：最适合创建摘要报告或控制面板。常用于汇总结果的最终命令。
+ `eventstats`：需要使用统计背景丰富事件以进行进一步分析或筛选时，这很有用。可在搜索过程中使用，以添加可在后续命令中使用的统计数据。

**语法**  
使用以下语法：

```
eventstats <aggregation>... [by-clause]    
```

**聚合**
+ 必需。
+ 聚合函数。
+ 聚合的参数必须是一个字段。

**by-clause**
+ 可选。
+ 语法：`by [span-expression,] [field,]...`
+ by 子句可以包含字段和表达式，例如标量函数和聚合函数。也可以使用 span 子句将特定字段拆分为间隔相等的存储桶。eventstats 命令随后基于这些 span 存储桶执行聚合操作。
+ 默认：如果未指定 by 子句，eventstats 命令将对整个结果集进行聚合。

**span-expression**
+ 可选，最多一个。
+ 语法：`span(field_expr, interval_expr)`
+ 默认情况下，间隔表达式的单位为自然单位。然而，对于日期和时间类型的字段，使用日期/时间单位时，需要在间隔表达式中指定单位。

  例如，要按照 10 年为单位将 `age` 字段拆分为存储桶，请使用 `span(age, 10)`。对于基于时间的字段，可使用 `span(timestamp, 1h)` 将 `timestamp` 字段拆分为每小时间隔。


**可用时间单位**  

| 跨度单位 | 
| --- | 
| 毫秒（ms） | 
| 秒（s） | 
| 分钟（m，区分大小写） | 
| 小时（h） | 
| 天（d） | 
| 周（w） | 
| 月（M，区分大小写） | 
| 季度（q） | 
| 年（y） | 

**聚合函数**  


**`COUNT`**  
`COUNT` 返回 SELECT 语句检索到的行中 expr 出现的次数。

对于 CloudWatch 日志，`COUNT`不支持使用查询。

示例：

```
os> source=accounts | eventstats count();
fetched rows / total rows = 4/4
+----------------+----------+-----------+----------+-----+--------+--------------------+------------+--------------------------+--------+-------+---------+
| account_number | balance  | firstname | lastname | age | gender | address            | employer   | email                    | city   | state | count() |
+----------------+----------+-----------+----------+-----+--------+--------------------+------------+--------------------------+--------+-------+---------+
| 1              | 39225    | Jane      | Doe      | 32  | M      | *** Any Lane       | AnyCorp    | janedoe@anycorp.com      | Brogan | IL    | 4       |
| 6              | 5686     | Mary      | Major    | 36  | M      | 671 Example Street | AnyCompany | marymajor@anycompany.com | Dante  | TN    | 4       |
| 13             | 32838    | Nikki     | Wolf     | 28  | F      | 789 Any Street     | AnyOrg     |                          | Nogal  | VA    | 4       |
| 18             | 4180     | Juan      | Li       | 33  | M      | *** Example Court  |            | juanli@exampleorg.com    | Orick  | MD    | 4       |
+----------------+----------+-----------+----------+-----+--------+--------------------+------------+--------------------------+--------+-------+---------+
```

**`SUM`**  
`SUM(expr)` 返回 expr 的和。

示例：

```
os> source=accounts | eventstats sum(age) by gender;
fetched rows / total rows = 4/4
+----------------+----------+-----------+----------+-----+--------+-----------------------+------------+--------------------------+--------+-------+--------------------+
| account_number | balance  | firstname | lastname | age | gender | address               | employer   | email                    | city   | state | sum(age) by gender |
+----------------+----------+-----------+----------+-----+--------+-----------------------+------------+--------------------------+--------+-------+--------------------+
| 1              | 39225    | Jane      | Doe      | 32  | M      | 880 Any Lane          | AnyCorp    | janedoe@anycorp.com      | Brogan | IL    | 101                |
| 6              | 5686     | Mary      | Major    | 36  | M      | 671 Example Street    | AnyCompany | marymajor@anycompany.com | Dante  | TN    | 101                |
| 13             | 32838    | Nikki     | Wolf     | 28  | F      | 789 Any Street        | AnyOrg     |                          | Nogal  | VA    | 28                 |
| 18             | 4180     | Juan      | Li       | 33  | M      | 467 Example Court     |            | juanli@exampleorg.com    | Orick  | MD    | 101                |
+----------------+----------+-----------+----------+-----+--------+-----------------------+------------+--------------------------+--------+-------+--------------------+
```

**`AVG`**  
`AVG(expr)` 返回 expr 的平均值。

示例：

```
os> source=accounts | eventstats avg(age) by gender;
fetched rows / total rows = 4/4
+----------------+----------+-----------+----------+-----+--------+-----------------------+------------+---------------------------+--------+-------+--------------------+
| account_number | balance  | firstname | lastname | age | gender | address               | employer    | email                    | city   | state | avg(age) by gender |
+----------------+----------+-----------+----------+-----+--------+-----------------------+------------+---------------------------+--------+-------+--------------------+
| 1              | 39225    | Jane      | Doe      | 32  | M      | 880 Any Lane          | AnyCorp     | janedoe@anycorp.com      | Brogan | IL    | 33.67              |
| 6              | 5686     | Mary      | Major    | 36  | M      | 671 Example Street    | Any Company | marymajor@anycompany.com | Dante  | TN    | 33.67              |
| 13             | 32838    | Nikki     | Wolf     | 28  | F      | 789 Any Street        | AnyOrg      |                          | Nogal  | VA    | 28.00              |
| 18             | 4180     | Juan      | Li       | 33  | M      | 467 Example Court     |             | juanli@exampleorg.com    | Orick  | MD    | 33.67              |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+--------------------+
```

**MAX**  
`MAX(expr)` 返回 expr 的最大值。

示例

```
os> source=accounts | eventstats max(age);
fetched rows / total rows = 4/4
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+-----------+
| account_number | balance  | firstname | lastname | age | gender | address               | employer    | email                    | city   | state | max(age)  |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+-----------+
| 1              | 39225    | Jane      | Doe      | 32  | M      | 880 Any Lane          | AnyCorp     | janedoe@anycorp.com      | Brogan | IL    | 36        |
| 6              | 5686     | Mary      | Major    | 36  | M      | 671 Example Street    | Any Company | marymajor@anycompany.com | Dante  | TN    | 36        |
| 13             | 32838    | Nikki     | Wolf     | 28  | F      | 789 Any Street        | AnyOrg      |                          | Nogal  | VA    | 36        |
| 18             | 4180     | Juan      | Li       | 33  | M      | *** Example Court     |             | juanli@exampleorg.com    | Orick  | MD    | 36        |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+-----------+
```

**MIN**  
`MIN(expr)` 返回 expr 的最小值。

示例

```
os> source=accounts | eventstats min(age);
fetched rows / total rows = 4/4
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+-----------+
| account_number | balance  | firstname | lastname | age | gender | address               | employer    | email                    | city   | state | min(age)  |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+-----------+
| 1              | 39225    | Jane      | Doe      | 32  | M      | 880 Any Lane          | AnyCorp     | janedoe@anycorp.com      | Brogan | IL    | 28        |
| 6              | 5686     | Mary      | Major    | 36  | M      | 671 Example Street    | Any Company | marymajor@anycompany.com | Dante  | TN    | 28        |
| 13             | 32838    | Nikki     | Wolf     | 28  | F      | *** Any Street        | AnyOrg      |                          | Nogal  | VA    | 28        |
| 18             | 4180     | Juan      | Li       | 33  | M      | *** Example Court     |             | juanli@exampleorg.com    | Orick  | MD    | 28        |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+-----------+
```

**STDDEV\$1SAMP**  
`STDDEV_SAMP(expr)` 返回 expr 的样本标准差。

示例

```
os> source=accounts | eventstats stddev_samp(age);
fetched rows / total rows = 4/4
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+------------------------+
| account_number | balance  | firstname | lastname | age | gender | address               | employer    | email                    | city   | state | stddev_samp(age)       |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+------------------------+
| 1              | 39225    | Jane      | Doe      | 32  | M      | *** Any Lane          | AnyCorp     | janedoe@anycorp.com      | Brogan | IL    | 3.304037933599835      |
| 6              | 5686     | Mary      | Major    | 36  | M      | 671 Example Street    | Any Company | marymajor@anycompany.com | Dante  | TN    | 3.304037933599835      |
| 13             | 32838    | Nikki     | Wolf     | 28  | F      | 789 Any Street        | AnyOrg      |                          | Nogal  | VA    | 3.304037933599835      |
| 18             | 4180     | Juan      | Li       | 33  | M      | 467 Example Court     |             | juanli@exampleorg.com    | Orick  | MD    | 3.304037933599835      |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+------------------------+
```

**STDDEV\$1POP**  
`STDDEV_POP(expr)` 返回 expr 的总体标准差。

示例

```
os> source=accounts | eventstats stddev_pop(age);
fetched rows / total rows = 4/4
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+------------------------+
| account_number | balance  | firstname | lastname | age | gender | address               | employer    | email                    | city   | state | stddev_pop(age)        |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+------------------------+
| 1              | 39225    | Jane      | Doe      | 32  | M      | 880 Any Lane          | AnyCorp     | janedoe@anycorp.com      | Brogan | IL    | 2.****************     |
| 6              | 5686     | Mary      | Major    | 36  | M      | *** Example Street    | Any Company | marymajor@anycompany.com | Dante  | TN    | 2.****************     |
| 13             | 32838    | Nikki     | Wolf     | 28  | F      | *** Any Street        | AnyOrg      |                          | Nogal  | VA    | 2.****************     |
| 18             | 4180     | Juan      | Li       | 33  | M      | *** Example Court     |             | juanli@exampleorg.com    | Orick  | MD    | 2.****************     |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+------------------------+
```

**PERCENTILE 或 PERCENTILE\$1APPROX**  
`PERCENTILE(expr, percent)` 或 `PERCENTILE_APPROX(expr, percent)` 返回 expr 在指定百分比处的近似百分位数值。

**百分比**
+ 该数值必须是 0 到 100 之间的常数。

示例

```
os> source=accounts | eventstats percentile(age, 90) by gender;
fetched rows / total rows = 4/4
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+--------------------------------+
| account_number | balance  | firstname | lastname | age | gender | address               | employer    | email                    | city   | state | percentile(age, 90) by gender  |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+--------------------------------+
| 1              | 39225    | Jane      | Doe      | 32  | M      | *** Any Lane          | AnyCorp     | janedoe@anycorp.com      | Brogan | IL    | 36                             |
| 6              | 5686     | Mary      | Major    | 36  | M      | 671 Example Street    | Any Company | marymajor@anycompany.com | Dante  | TN    | 36                             |
| 13             | 32838    | Nikki     | Wolf     | 28  | F      | 789 Any Street        | AnyOrg      |                          | Nogal  | VA    | 28                             |
| 18             | 4180     | Juan      | Li       | 33  | M      | *** Example Court     |             | juanli@exampleorg.com    | Orick  | MD    | 36                             |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+--------------------------------+
```

**示例 1：按组计算字段的平均值、总和及计数**  
该示例显示按性别分组计算所有账户的平均年龄、总年龄和事件计数。

```
os> source=accounts | eventstats avg(age) as avg_age, sum(age) as sum_age, count() as count by gender;
fetched rows / total rows = 4/4
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+-----------+-----------+-------+
| account_number | balance  | firstname | lastname | age | gender | address               | employer    | email                    | city   | state | avg_age   | sum_age   | count |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+-----------+-----------+-------+
| 1              | 39225    | Jane      | Doe      | 32  | M      | *** Any Lane          | AnyCorp     | janedoe@anycorp.com      | Brogan | IL    | 33.666667 | 101       | 3     |
| 6              | 5686     | Mary      | Major    | 36  | M      | 671 Example Street    | Any Company | marymajor@anycompany.com | Dante  | TN    | 33.666667 | 101       | 3     |
| 13             | 32838    | Nikki     | Wolf     | 28  | F      | 789 Any Street        | AnyOrg      |                          | Nogal  | VA    | 28.000000 | 28        | 1     |
| 18             | 4180     | Juan      | Li       | 33  | M      | *** Example Court     |             | juanli@exampleorg.com    | Orick  | MD    | 33.666667 | 101       | 3     |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+-----------+-----------+-------+
```

**示例 2：按跨度计算计数**  
该示例以 10 年为间隔统计年龄计数。

```
os> source=accounts | eventstats count(age) by span(age, 10) as age_span
fetched rows / total rows = 4/4
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+----------+
| account_number | balance  | firstname | lastname | age | gender | address               | employer    | email                    | city   | state | age_span |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+----------+
| 1              | 39225    | Jane      | Doe      | 32  | M      | *** Any Lane          | AnyCorp     | janedoe@anycorp.com      | Brogan | IL    | 3        |
| 6              | 5686     | Mary      | Major    | 36  | M      | 671 Example Street    | Any Company | marymajor@anycompany.com | Dante  | TN    | 3        |
| 13             | 32838    | Nikki     | Wolf     | 28  | F      | 789 Any Street        | AnyOrg      |                          | Nogal  | VA    | 1        |
| 18             | 4180     | Juan      | Li       | 33  | M      | *** Example Court     |             | juanli@exampleorg.com    | Orick  | MD    | 3        |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+--------------------------+--------+-------+----------+
```

**示例 3：按性别和跨度计算计数**  
该示例以 5 年为间隔统计年龄计数，并按性别进行分组。

```
os> source=accounts | eventstats count() as cnt by span(age, 5) as age_span, gender
fetched rows / total rows = 4/4
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+---------------------------+--------+-------+-----+
| account_number | balance  | firstname | lastname | age | gender | address               | employer    | email                     | city   | state | cnt |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+---------------------------+--------+-------+-----+
| 1              | 39225    | Jane      | Doe      | 32  | M      | *** Any Lane          | AnyCorp     | janedoe@anycorp.com       | Brogan | IL    | 2   |
| 6              | 5686     | Mary      | Majo     | 36  | M      | 671 Example Street    | Any Company | hattiebond@anycompany.com | Dante  | TN    | 1   |
| 13             | 32838    | Nikki     | Wolf     | 28  | F      | *** Any Street        | AnyOrg      |                           | Nogal  | VA    | 1   |
| 18             | 4180     | Juan      | Li       | 33  | M      | *** Example Court     |             | juanli@exampleorg.com     | Orick  | MD    | 2   |
+----------------+----------+-----------+----------+-----+--------+-----------------------+-------------+---------------------------+--------+-------+-----+
```

**用法**
+ `source = table | eventstats avg(a)`
+ `source = table | where a < 50 | eventstats avg(c)`
+ `source = table | eventstats max(c) by b`
+ `source = table | eventstats count(c) by b | head 5`
+ `source = table | eventstats distinct_count(c)`
+ `source = table | eventstats stddev_samp(c)`
+ `source = table | eventstats stddev_pop(c)`
+ `source = table | eventstats percentile(c, 90)`
+ `source = table | eventstats percentile_approx(c, 99)`

**带跨度聚合**  

+ `source = table | eventstats count(a) by span(a, 10) as a_span`
+ `source = table | eventstats sum(age) by span(age, 5) as age_span | head 2`
+ `source = table | eventstats avg(age) by span(age, 20) as age_span, country | sort - age_span | head 2`

**具有时间窗跨度的聚合（翻转窗口函数）**  

+ `source = table | eventstats sum(productsAmount) by span(transactionDate, 1d) as age_date | sort age_date`
+ `source = table | eventstats sum(productsAmount) by span(transactionDate, 1w) as age_date, productId`

**按多个级别对聚合分组**  

+ `source = table | eventstats avg(age) as avg_state_age by country, state | eventstats avg(avg_state_age) as avg_country_age by country`
+ `source = table | eventstats avg(age) as avg_city_age by country, state, city | eval new_avg_city_age = avg_city_age - 1 | eventstats avg(new_avg_city_age) as avg_state_age by country, state | where avg_state_age > 18 | eventstats avg(avg_state_age) as avg_adult_country_age by country`

#### expand 命令
<a name="supported-ppl-expand-commands"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

使用 `expand` 命令，展平以下类型的字段：
+ `Array<Any>`
+ `Map<Any>`

**语法**  
使用以下语法：

```
expand <field> [As alias]
```

**字段**
+ 要扩展（展开）的字段。必须是受支持的类型。

**别名**
+ 可选。要使用的名称，而非原始字段名称。

**用法**  
`expand` 命令为指定数组或映射字段中的每个元素生成一行，其中：
+ 数组元素单独成行。
+ 映射键值对拆分为不同的行，每个键值都表示为一行。
+ 提供别名时，展开后的值将显示在别名下，而非原始字段名称下。
+ 这可与其他命令（例如 `stats`、`eval` 和 `parse`）结合使用，用于在扩展后对数据进行操作或提取。

**示例**
+ `source = table | expand employee | stats max(salary) as max by state, company`
+ `source = table | expand employee as worker | stats max(salary) as max by state, company`
+ `source = table | expand employee as worker | eval bonus = salary * 3 | fields worker, bonus`
+ `source = table | expand employee | parse description '(?<email>.+@.+)' | fields employee, email`
+ `source = table | eval array=json_array(1, 2, 3) | expand array as uid | fields name, occupation, uid`
+ `source = table | expand multi_valueA as multiA | expand multi_valueB as multiB`

#### explain 命令
<a name="supported-ppl-explain-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

`explain` 命令可帮助您理解查询执行计划，以分析和优化查询，从而提升性能。本节简要概述 explain 命令的用途及其在查询优化中的重要性。

**Comment**
+ `source=accounts | top gender // finds most common gender of all the accounts`（行注释）
+ `source=accounts | dedup 2 gender /* dedup the document with gender field keep 2 duplication */ | fields account_number, gender`（块注释）

**描述**
+ `describe table` 此命令等同于 `DESCRIBE EXTENDED table` SQL 命令
+ `describe schema.table`
+ `describe schema.`table``
+ `describe catalog.schema.table`
+ `describe catalog.schema.`table``
+ `describe `catalog`.`schema`.`table``

**解释**
+ `explain simple | source = table | where a = 1 | fields a,b,c`
+ `explain extended | source = table`
+ `explain codegen | source = table | dedup a | fields a,b,c`
+ `explain cost | source = table | sort a | fields a,b,c`
+ `explain formatted | source = table | fields - a`
+ `explain simple | describe table`

**字段**
+ `source = table`
+ `source = table | fields a,b,c`
+ `source = table | fields + a,b,c`
+ `source = table | fields - b,c`
+ `source = table | eval b1 = b | fields - b1,c`

**字段摘要**
+ `source = t | fieldsummary includefields=status_code nulls=false`
+ `source = t | fieldsummary includefields= id, status_code, request_path nulls=true`
+ `source = t | where status_code != 200 | fieldsummary includefields= status_code nulls=true`

**嵌套字段**
+ `source = catalog.schema.table1, catalog.schema.table2 | fields A.nested1, B.nested1`
+ `source = catalog.table | where struct_col2.field1.subfield > 'valueA' | sort int_col | fields int_col, struct_col.field1.subfield, struct_col2.field1.subfield`
+ `source = catalog.schema.table | where struct_col2.field1.subfield > 'valueA' | sort int_col | fields int_col, struct_col.field1.subfield, struct_col2.field1.subfield`

**筛选条件**
+ `source = table | where a = 1 | fields a,b,c`
+ `source = table | where a >= 1 | fields a,b,c`
+ `source = table | where a < 1 | fields a,b,c`
+ `source = table | where b != 'test' | fields a,b,c`
+ `source = table | where c = 'test' | fields a,b,c | head 3`
+ `source = table | where ispresent(b)`
+ `source = table | where isnull(coalesce(a, b)) | fields a,b,c | head 3`
+ `source = table | where isempty(a)`
+ `source = table | where isblank(a)`
+ `source = table | where case(length(a) > 6, 'True' else 'False') = 'True'`
+ `source = table | where a not in (1, 2, 3) | fields a,b,c`
+ `source = table | where a between 1 and 4`：注意：这将返回 >= 1 和 <= 4，即 [1, 4]
+ `source = table | where b not between '2024-09-10' and '2025-09-10'`：注意：这将返回 b >= '\$1\$1\$1\$1\$1\$1\$1\$1\$1\$1 '和 b <=' 2025-09-10 '
+ `source = table | where cidrmatch(ip, '***********/24')`
+ `source = table | where cidrmatch(ipv6, '2003:db8::/32')`
+ `source = table | trendline sma(2, temperature) as temp_trend`

**IP 相关查询**
+ `source = table | where cidrmatch(ip, '**************')`
+ `source = table | where isV6 = false and isValid = true and cidrmatch(ipAddress, '**************')`
+ `source = table | where isV6 = true | eval inRange = case(cidrmatch(ipAddress, '2003:***::/32'), 'in' else 'out') | fields ip, inRange`

**复杂筛选条件**  


```
source = table | eval status_category =
case(a >= 200 AND a < 300, 'Success',
    a >= 300 AND a < 400, 'Redirection',
    a >= 400 AND a < 500, 'Client Error',
    a >= 500, 'Server Error'
else 'Incorrect HTTP status code')
| where case(a >= 200 AND a < 300, 'Success',
    a >= 300 AND a < 400, 'Redirection',
    a >= 400 AND a < 500, 'Client Error',
    a >= 500, 'Server Error'
else 'Incorrect HTTP status code'
) = 'Incorrect HTTP status code'
```

```
source = table
| eval factor = case(a > 15, a - 14, isnull(b), a - 7, a < 3, a + 1 else 1)
| where case(factor = 2, 'even', factor = 4, 'even', factor = 6, 'even', factor = 8, 'even' else 'odd') = 'even'
| stats count() by factor
```

**具有逻辑条件的筛选器**
+ `source = table | where c = 'test' AND a = 1 | fields a,b,c`
+ `source = table | where c != 'test' OR a > 1 | fields a,b,c | head 1`
+ `source = table | where c = 'test' NOT a > 1 | fields a,b,c`

**Eval**  
假设：`a`、`b`、`c` 是 `table` 中的现有存在字段
+ `source = table | eval f = 1 | fields a,b,c,f`
+ `source = table | eval f = 1`（输出 a、b、c、f 字段）
+ `source = table | eval n = now() | eval t = unix_timestamp(a) | fields n,t`
+ `source = table | eval f = a | where f > 1 | sort f | fields a,b,c | head 5`
+ `source = table | eval f = a * 2 | eval h = f * 2 | fields a,f,h`
+ `source = table | eval f = a * 2, h = f * 2 | fields a,f,h`
+ `source = table | eval f = a * 2, h = b | stats avg(f) by h`
+ `source = table | eval f = ispresent(a)`
+ `source = table | eval r = coalesce(a, b, c) | fields r`
+ `source = table | eval e = isempty(a) | fields e`
+ `source = table | eval e = isblank(a) | fields e`
+ `source = table | eval f = case(a = 0, 'zero', a = 1, 'one', a = 2, 'two', a = 3, 'three', a = 4, 'four', a = 5, 'five', a = 6, 'six', a = 7, 'se7en', a = 8, 'eight', a = 9, 'nine')`
+ `source = table | eval f = case(a = 0, 'zero', a = 1, 'one' else 'unknown')`
+ `source = table | eval f = case(a = 0, 'zero', a = 1, 'one' else concat(a, ' is an incorrect binary digit'))`
+ `source = table | eval digest = md5(fieldName) | fields digest`
+ `source = table | eval digest = sha1(fieldName) | fields digest`
+ `source = table | eval digest = sha2(fieldName,256) | fields digest`
+ `source = table | eval digest = sha2(fieldName,512) | fields digest`

#### fillnull 命令
<a name="supported-ppl-fillnull-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

**说明**  
使用 `fillnull` 命令，将搜索结果的一个或多个字段中的 null 值替换为指定值。

**语法**  
使用以下语法：

```
fillnull [with <null-replacement> in <nullable-field>["," <nullable-field>]] | [using <source-field> = <null-replacement> [","<source-field> = <null-replacement>]]
```
+ null-replacement：必需。用于替换 null 值的值。
+ nullable-field：必需。字段参考。此字段中的 null 值将替换为 null-replacement 中指定的值。

**示例 1：Fillnull 一个字段**  
该示例展示如何在单个字段上使用 fillnull：

```
os> source=logs | fields status_code | eval input=status_code | fillnull with 0 in status_code;
| input | status_code |
|-------|-------------|
| 403   | 403         |
| 403   | 403         |
| NULL  | 0           |
| NULL  | 0           |
| 200   | 200         |
| 404   | 404         |
| 500   | 500         |
| NULL  | 0           |
| 500   | 500         |
| 404   | 404         |
| 200   | 200         |
| 500   | 500         |
| NULL  | 0           |
| NULL  | 0           |
| 404   | 404         |
```

**示例 2：将 Fillnull 应用于多个字段**  
该示例展示应用于多个字段的 fillnull。

```
os> source=logs | fields request_path, timestamp | eval input_request_path=request_path, input_timestamp = timestamp | fillnull with '???' in request_path, timestamp;
| input_request_path | input_timestamp       | request_path | timestamp              |
|------------------------------------------------------------------------------------|
| /contact           | NULL                  | /contact     | ???                    |
| /home              | NULL                  | /home        | ???                    |
| /about             | 2023-10-01 10:30:00   | /about       | 2023-10-01 10:30:00    |
| /home              | 2023-10-01 10:15:00   | /home        | 2023-10-01 10:15:00    |
| NULL               | 2023-10-01 10:20:00   | ???          | 2023-10-01 10:20:00    |
| NULL               | 2023-10-01 11:05:00   | ???          | 2023-10-01 11:05:00    |
| /about             | NULL                  | /about       | ???                    |
| /home              | 2023-10-01 10:00:00   | /home        | 2023-10-01 10:00:00    |
| /contact           | NULL                  | /contact     | ???                    |
| NULL               | 2023-10-01 10:05:00   | ???          | 2023-10-01 10:05:00    |
| NULL               | 2023-10-01 10:50:00   | ???          | 2023-10-01 10:50:00    |
| /services          | NULL                  | /services    | ???                    |
| /home              | 2023-10-01 10:45:00   | /home        | 2023-10-01 10:45:00    |
| /services          | 2023-10-01 11:00:00   | /services    | 2023-10-01 11:00:00    |
| NULL               | 2023-10-01 10:35:00   | ???          | 2023-10-01 10:35:00    |
```

**示例 3：将 Fillnull 应用于多个字段，且各字段具有不同的 null 替换值。**  
该示例展示使用多种值替换 null 值的 fillnull 方法。
+ `request_path` 字段中的 `/error`
+ `timestamp` 字段中的 `1970-01-01 00:00:00`

```
os> source=logs | fields request_path, timestamp | eval input_request_path=request_path, input_timestamp = timestamp | fillnull using request_path = '/error', timestamp='1970-01-01 00:00:00';

| input_request_path | input_timestamp       | request_path | timestamp              |
|------------------------------------------------------------------------------------|
| /contact           | NULL                  | /contact     | 1970-01-01 00:00:00    |
| /home              | NULL                  | /home        | 1970-01-01 00:00:00    |
| /about             | 2023-10-01 10:30:00   | /about       | 2023-10-01 10:30:00    |
| /home              | 2023-10-01 10:15:00   | /home        | 2023-10-01 10:15:00    |
| NULL               | 2023-10-01 10:20:00   | /error       | 2023-10-01 10:20:00    |
| NULL               | 2023-10-01 11:05:00   | /error       | 2023-10-01 11:05:00    |
| /about             | NULL                  | /about       | 1970-01-01 00:00:00    |
| /home              | 2023-10-01 10:00:00   | /home        | 2023-10-01 10:00:00    |
| /contact           | NULL                  | /contact     | 1970-01-01 00:00:00    |
| NULL               | 2023-10-01 10:05:00   | /error       | 2023-10-01 10:05:00    |
| NULL               | 2023-10-01 10:50:00   | /error       | 2023-10-01 10:50:00    |
| /services          | NULL                  | /services    | 1970-01-01 00:00:00    |
| /home              | 2023-10-01 10:45:00   | /home        | 2023-10-01 10:45:00    |
| /services          | 2023-10-01 11:00:00   | /services    | 2023-10-01 11:00:00    |
| NULL               | 2023-10-01 10:35:00   | /error       | 2023-10-01 10:35:00    |
```

#### fields 命令
<a name="supported-ppl-fields-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

使用 `fields` 命令，保留或删除搜索结果中的字段。

**语法**  
使用以下语法：

```
field [+|-] <field-list> 
```
+ `index`: 可选。

  如果使用加号 (\$1)，则仅保留字段列表中指定的字段。

  如果使用减号 (-)，则删除字段列表中指定的所有字段。

  *默认*：\$1
+ `field list`：必需。要保留或删除的字段列表，以逗号分隔。

**示例 1：从结果中选择指定字段**  
此示例展示如何从搜索结果中提取 `account_number`、`firstname` 和 `lastname` 字段。

PPL 查询：

```
os> source=accounts | fields account_number, firstname, lastname;
fetched rows / total rows = 4/4
+------------------+-------------+------------+
| account_number   | firstname   | lastname   |
|------------------+-------------+------------|
| 1                | Jane        | Doe        |
| 6                | John        | Doe        |
| 13               | Jorge       | Souza      |
| 18               | Juan        | Li         |
+------------------+-------------+------------+
```

**示例 2：从结果中移除指定字段**  
此示例展示如何从搜索结果中移除 `account_number` 字段。

PPL 查询：

```
os> source=accounts | fields account_number, firstname, lastname | fields - account_number ;
fetched rows / total rows = 4/4
+-------------+------------+
| firstname   | lastname   |
|-------------+------------|
| Jane        | Doe        |
| John        | Doe        |
| Jorge       | Souza      |
| Juan        | Li         |
+-------------+------------+
```

**其他示例**
+ `source = table`
+ `source = table | fields a,b,c`
+ `source = table | fields + a,b,c`
+ `source = table | fields - b,c`
+ `source = table | eval b1 = b | fields - b1,c`

嵌套字段示例：

```
`source = catalog.schema.table1, catalog.schema.table2 | fields A.nested1, B.nested1`
`source = catalog.table | where struct_col2.field1.subfield > 'valueA' | sort int_col | fields  int_col, struct_col.field1.subfield, struct_col2.field1.subfield`
`source = catalog.schema.table | where struct_col2.field1.subfield > 'valueA' | sort int_col | fields  int_col, struct_col.field1.subfield, struct_col2.field1.subfield`
```

#### flatten 命令
<a name="supported-ppl-flatten-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

使用 flatten 命令，展开以下类型的字段：
+ `struct<?,?>`
+ `array<struct<?,?>>`

**语法**  
使用以下语法：

```
flatten <field>
```
+ *字段*：要展平的字段。字段必须是受支持的类型。

**架构**


| col\$1name | data\$1type | 
| --- | --- | 
| \$1time | 字符串 | 
| bridges | array<struct<length:bigint,name:string>> | 
| city | 字符串 | 
| coor | struct<alt:bigint,lat:double,long:double> | 
| country | 字符串 | 

**数据**  



| \$1time | bridges | city | coor | country | 
| --- | --- | --- | --- | --- | 
| 2024-09-13T12:00:00 | [\$1801, Tower Bridge\$1, \$1928, London Bridge\$1] | 伦敦 | \$135, 51.5074, -0.1278\$1 | England | 
| 2024-09-13T12:00:00 | [\$1232, Pont Neuf\$1, \$1160, Pont Alexandre III\$1] | Paris | \$135, 48.8566, 2.3522\$1 | 法国 | 
| 2024-09-13T12:00:00 | [\$148, Rialto Bridge\$1, \$111, Bridge of Sighs\$1] | 威尼斯 | \$12, 45.4408, 12.3155\$1 | 意大利 | 
| 2024-09-13T12:00:00 | [\$1\$1\$1\$1, Charles Bridge\$1, \$1343, Legion Bridge\$1] | 布拉格 | \$1200, 50.0755, 14.4378\$1 | 捷克共和国 | 
| 2024-09-13T12:00:00 | [\$1375, Chain Bridge\$1, \$1333, Liberty Bridge\$1] | 布达佩斯 | \$196, 47.4979, 19.0402\$1 | 匈牙利 | 
| 1990-09-13T 12:00:00 | NULL | 华沙 | NULL | 波兰 | 

**示例 1：展平结构**  
此示例说明如何对结构字段进行展平处理。

PPL 查询：

```
source=table | flatten coor
```


| \$1time | bridges | city | country | alt | lat | 长整数 | 
| --- | --- | --- | --- | --- | --- | --- | 
| 2024-09-13T12:00:00 | [\$1801, Tower Bridge\$1, \$1928, London Bridge\$1] | 伦敦 | England | 35 | 51.5074 | -0.1278 | 
| 2024-09-13T12:00:00 | [\$1232, Pont Neuf\$1, \$1160, Pont Alexandre III\$1] | Paris | 法国 | 35 | 48.8566 | 2.3522 | 
| 2024-09-13T12:00:00 | [\$148, Rialto Bridge\$1, \$111, Bridge of Sighs\$1] | 威尼斯 | 意大利 | 2 | 45.4408 | 12.3155 | 
| 2024-09-13T12:00:00 | [\$1516, Charles Bridge\$1, \$1343, Legion Bridge\$1] | 布拉格 | 捷克共和国 | 200 | 50.0755 | 14.4378 | 
| 2024-09-13T12:00:00 | [\$1375, Chain Bridge\$1, \$1333, Liberty Bridge\$1] | 布达佩斯 | 匈牙利 | 96 | 47.4979 | 19.0402 | 
| 1990-09-13T 12:00:00 | NULL | 华沙 | 波兰 | NULL | NULL | NULL | 

**示例 2：展平数组**  
该示例说明如何对结构字段的数组进行展平处理。

PPL 查询：

```
source=table | flatten bridges
```


| \$1time | city | coor | country | length | name | 
| --- | --- | --- | --- | --- | --- | 
| 2024-09-13T12:00:00 | 伦敦 | \$135, 51.5074, -0.1278\$1 | England | 801 | 塔桥 | 
| 2024-09-13T12:00:00 | 伦敦 | \$135, 51.5074, -0.1278\$1 | England | 928 | 伦敦桥 | 
| 2024-09-13T12:00:00 | Paris | \$135, 48.8566, 2.3522\$1 | 法国 | 232 | Pont Neuf | 
| 2024-09-13T12:00:00 | Paris | \$135, 48.8566, 2.3522\$1 | 法国 | 160 | 亚历山大三世桥 | 
| 2024-09-13T12:00:00 | 威尼斯 | \$12, 45.4408, 12.3155\$1 | 意大利 | 48 | 里亚托桥 | 
| 2024-09-13T12:00:00 | 威尼斯 | \$12, 45.4408, 12.3155\$1 | 意大利 | 11 | 叹息桥 | 
| 2024-09-13T12:00:00 | 布拉格 | \$1200, 50.0755, 14.4378\$1 | 捷克共和国 | 516 | 查理大桥 | 
| 2024-09-13T12:00:00 | 布拉格 | \$1200, 50.0755, 14.4378\$1 | 捷克共和国 | 343 | 军团大桥 | 
| 2024-09-13T12:00:00 | 布达佩斯 | \$196, 47.4979, 19.0402\$1 | 匈牙利 | 375 | 链桥 | 
| 2024-09-13T12:00:00 | 布达佩斯 | \$196, 47.4979, 19.0402\$1 | 匈牙利 | 333 | 自由大桥 | 
| 1990-09-13T 12:00:00 | 华沙 | NULL | 波兰 | NULL | NULL | 

**示例 3：展平数组和结构**  
此示例说明如何对多个字段进行展平处理。

PPL 查询：

```
source=table | flatten bridges | flatten coor
```


| \$1time | city | country | length | name | alt | lat | 长整数 | 
| --- | --- | --- | --- | --- | --- | --- | --- | 
| 2024-09-13T12:00:00 | 伦敦 | England | 801 | 塔桥 | 35 | 51.5074 | -0.1278 | 
| 2024-09-13T12:00:00 | 伦敦 | England | 928 | 伦敦桥 | 35 | 51.5074 | -0.1278 | 
| 2024-09-13T12:00:00 | Paris | 法国 | 232 | Pont Neuf | 35 | 48.8566 | 2.3522 | 
| 2024-09-13T12:00:00 | Paris | 法国 | 160 | 亚历山大三世桥 | 35 | 48.8566 | 2.3522 | 
| 2024-09-13T12:00:00 | 威尼斯 | 意大利 | 48 | 里亚托桥 | 2 | 45.4408 | 12.3155 | 
| 2024-09-13T12:00:00 | 威尼斯 | 意大利 | 11 | 叹息桥 | 2 | 45.4408 | 12.3155 | 
| 2024-09-13T12:00:00 | 布拉格 | 捷克共和国 | 516 | 查理大桥 | 200 | 50.0755 | 14.4378 | 
| 2024-09-13T12:00:00 | 布拉格 | 捷克共和国 | 343 | 军团大桥 | 200 | 50.0755 | 14.4378 | 
| 2024-09-13T12:00:00 | 布达佩斯 | 匈牙利 | 375 | 链桥 | 96 | 47.4979 | 19.0402 | 
| 2024-09-13T12:00:00 | 布达佩斯 | 匈牙利 | 333 | 自由大桥 | 96 | 47.4979 | 19.0402 | 
| 1990-09-13T 12:00:00 | 华沙 | 波兰 | NULL | NULL | NULL | NULL | NULL | 

#### grok 命令
<a name="supported-ppl-grok-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

`grok` 命令使用 grok 模式解析文本字段，并将结果附加到搜索结果中。

**语法**  
使用以下语法：

```
grok <field> <pattern>
```

**字段**
+ 必需。
+ 该字段必须为文本字段。

**模式**
+ 必需。
+ 用于从给定文本字段提取新字段的 grok 模式。
+ 如果新的字段名称已存在，则会替换原有字段。

**Grok 模式**  
grok 模式用于匹配每个文档的文本字段，以提取新字段。

**示例 1：创建新字段**  
此示例说明如何为每个文档创建新字段 `host`。`host` 是 `email` 字段中接在 `@` 之后的主机名。解析 null 字段将返回空字符串。

```
os> source=accounts | grok email '.+@%{HOSTNAME:host}' | fields email, host ;
fetched rows / total rows = 4/4
+-------------------------+-------------+
| email                   | host        |
|-------------------------+-------------|
| jane_doe@example.com    | example.com |
| arnav_desai@example.net | example.net |
| null                    |             |
| juan_li@example.org     | example.org |
+-------------------------+-------------+
```

**示例 2：覆盖现有字段**  
此示例说明如何在移除门牌号的情况下覆盖现有 `address` 字段。

```
os> source=accounts | grok address '%{NUMBER} %{GREEDYDATA:address}' | fields address ;
fetched rows / total rows = 4/4
+------------------+
| address          |
|------------------|
| Example Lane     |
| Any Street       |
| Main Street      |
| Example Court    |
+------------------+
```

**示例 3：使用 grok 解析日志**  
此示例说明如何使用 grok 解析原始日志。

```
os> source=apache | grok message '%{COMMONAPACHELOG}' | fields COMMONAPACHELOG, timestamp, response, bytes ;
fetched rows / total rows = 4/4
+-----------------------------------------------------------------------------------------------------------------------------+----------------------------+------------+---------+
| COMMONAPACHELOG                                                                                                             | timestamp                  | response   | bytes   |
|-----------------------------------------------------------------------------------------------------------------------------+----------------------------+------------+---------|
| 177.95.8.74 - upton5450 [28/Sep/2022:10:15:57 -0700] "HEAD /e-business/mindshare HTTP/1.0" 404 19927                        | 28/Sep/2022:10:15:57 -0700 | 404        | 19927   |
| 127.45.152.6 - pouros8756 [28/Sep/2022:10:15:57 -0700] "GET /architectures/convergence/niches/mindshare HTTP/1.0" 100 28722 | 28/Sep/2022:10:15:57 -0700 | 100        | 28722   |
| *************** - - [28/Sep/2022:10:15:57 -0700] "PATCH /strategize/out-of-the-box HTTP/1.0" 401 27439                      | 28/Sep/2022:10:15:57 -0700 | 401        | 27439   |
| ************** - - [28/Sep/2022:10:15:57 -0700] "POST /users HTTP/1.1" 301 9481                                             | 28/Sep/2022:10:15:57 -0700 | 301        | 9481    |
+-----------------------------------------------------------------------------------------------------------------------------+----------------------------+------------+---------+
```

**限制**  
grok 命令与 parse 命令具有相同的限制。

#### head 命令
<a name="supported-ppl-head-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

使用 `head` 命令，返回搜索顺序中可选偏移量之后的前 N 个指定结果。

**语法**  
使用以下语法：

```
head [<size>] [from <offset>]
```

**<size>**
+ 可选整数。
+ 要返回的结果数量。
+ 默认值：10

**<offset>**
+ 可选 `from` 之后的整数。
+ 要跳过的结果数。
+ 默认：0

**示例 1：获取前 10 个结果**  
此示例说明如何从账户索引中检索最多 10 个结果。

PPL 查询：

```
os> source=accounts | fields firstname, age | head;
fetched rows / total rows = 4/4
+-------------+-------+
| firstname   | age   |
|-------------+-------|
| Jane        | 32    |
| John        | 36    |
| Jorge       | 28    |
| Juan        | 33    |
+-------------+-------+
```

**示例 2：获取前 N 个结果**  
该示例展示账户索引的前 N 个结果。

PPL 查询：

```
os> source=accounts | fields firstname, age | head 3;
fetched rows / total rows = 3/3
+-------------+-------+
| firstname   | age   |
|-------------+-------|
| Jane        | 32    |
| John        | 36    |
| Jorge       | 28    |
+-------------+-------+
```

**示例 3：获取偏移量 M 之后的前 N 个结果**  
此示例说明如何从账户索引中跳过 M 个结果后，检索后续的前 N 个结果。

PPL 查询：

```
os> source=accounts | fields firstname, age | head 3 from 1;
fetched rows / total rows = 3/3
+-------------+-------+
| firstname   | age   |
|-------------+-------|
| John        | 36    |
| Jorge       | 28    |
| Juan        | 33    |
+-------------+-------+
```

#### join 命令
<a name="supported-ppl-join-commands"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

join 命令允许您根据共同字段合并来自多个来源的数据，从而能够对分布式数据集进行复杂分析并获得更深入的见解

**架构**  
至少有两个索引，`otel-v1-apm-span-*`（大）和 `otel-v1-apm-service-map`（小）。

索引的相关字段：

**`otel-v1-apm-span-*`**
+ traceId：跟踪的唯一标识符。同一跟踪的所有跨度均共享相同的 traceId。
+ spanId：追踪中跨度的唯一标识符，在跨度创建时分配。
+ parentSpanId -此跨度的父跨度的 spanID。如果这是根跨度，则此字段必须为空。
+ durationInNanos -开始时间和结束时间之间的差异（以纳秒为单位）。 （这是`latency`在用户界面中）
+ serviceName：跨度所源自的资源。
+ traceGroup：跟踪的根跨度名称。

**`otel-v1-apm-service-map`**
+ serviceName：发出跨度的服务名称。
+ destination.domain：此客户端所调用服务的服务名称。
+ destination.resource：此客户端正在调用的跨度名称（API、操作等）。
+ target.domain：客户端所调用服务的服务名称。
+ target.resource：客户端正在调用的跨度名称（API、操作等）。
+ traceGroupName -启动请求链的顶级 span 名称。

**要求**  
支持 **join** 计算以下内容：

对于每项服务，将跨度索引与服务映射索引关联，以计算不同类型筛选条件下的指标。

此示例查询计算按跟踪组 `client_cancel_order` 筛选 `order` 服务时的延迟。

```
SELECT avg(durationInNanos)
FROM `otel-v1-apm-span-000001` t1
WHERE t1.serviceName = `order`
  AND ((t1.name in
          (SELECT target.resource
           FROM `otel-v1-apm-service-map`
           WHERE serviceName = `order`
             AND traceGroupName = `client_cancel_order`)
        AND t1.parentSpanId != NULL)
       OR (t1.parentSpanId = NULL
           AND t1.name = `client_cancel_order`))
  AND t1.traceId in
    (SELECT traceId
     FROM `otel-v1-apm-span-000001`
     WHERE serviceName = `order`)
```

**迁移到 PPL**  
join 命令的语法

```
SEARCH source=<left-table>
| <other piped command>
| [joinType] JOIN
    [leftAlias]
    ON joinCriteria
    <right-table>
| <other piped command>
```

**重写**  


```
SEARCH source=otel-v1-apm-span-000001
| WHERE serviceName = 'order'
| JOIN left=t1 right=t2
    ON t1.traceId = t2.traceId AND t2.serviceName = 'order'
    otel-v1-apm-span-000001 -- self inner join
| EVAL s_name = t1.name -- rename to avoid ambiguous
| EVAL s_parentSpanId = t1.parentSpanId -- RENAME command would be better when it is supported
| EVAL s_durationInNanos = t1.durationInNanos 
| FIELDS s_name, s_parentSpanId, s_durationInNanos -- reduce colunms in join
| LEFT JOIN left=s1 right=t3
    ON s_name = t3.target.resource AND t3.serviceName = 'order' AND t3.traceGroupName = 'client_cancel_order'
    otel-v1-apm-service-map
| WHERE (s_parentSpanId IS NOT NULL OR (s_parentSpanId IS NULL AND s_name = 'client_cancel_order'))
| STATS avg(s_durationInNanos) -- no need to add alias if there is no ambiguous
```

**joinType**
+ 语法：`INNER | LEFT OUTER | CROSS`
+ 可选
+ 要执行的联接类型。如果未指定，则默认为 `INNER`。

**leftAlias**
+ 语法：`left = <leftAlias>`
+ 可选
+ 用于左联接侧的子查询别名，以避免命名歧义。

**joinCriteria**
+ 语法：`<expression>`
+ 必需
+ 语法以 `ON` 开头。可以是任何比较表达式。通常，联接标准如 `<leftAlias>.<leftField>=<rightAlias>.<rightField>` 所示。

  例如：`l.id = r.id`。如果联接标准包含多个条件，则可在每个比较表达式之间指定 `AND` 和 `OR` 运算符。例如 `l.id = r.id AND l.email = r.email AND (r.age > 65 OR r.age < 18)`。

**更多示例**  
从 SQL 查询迁移（TPC-H Q13）：

```
SELECT c_count, COUNT(*) AS custdist
FROM
  ( SELECT c_custkey, COUNT(o_orderkey) c_count
    FROM customer LEFT OUTER JOIN orders ON c_custkey = o_custkey
        AND o_comment NOT LIKE '%unusual%packages%'
    GROUP BY c_custkey
  ) AS c_orders
GROUP BY c_count
ORDER BY custdist DESC, c_count DESC;
```

由 PPL 联接查询重写：

```
SEARCH source=customer
| FIELDS c_custkey
| LEFT OUTER JOIN
    ON c_custkey = o_custkey AND o_comment NOT LIKE '%unusual%packages%'
    orders
| STATS count(o_orderkey) AS c_count BY c_custkey
| STATS count() AS custdist BY c_count
| SORT - custdist, - c_count
```

限制：右联接侧不支持子搜索。

如果支持子搜索，则可将上述 PPL 查询重写为如下形式：

```
SEARCH source=customer
| FIELDS c_custkey
| LEFT OUTER JOIN
   ON c_custkey = o_custkey
   [
      SEARCH source=orders
      | WHERE o_comment NOT LIKE '%unusual%packages%'
      | FIELDS o_orderkey, o_custkey
   ]
| STATS count(o_orderkey) AS c_count BY c_custkey
| STATS count() AS custdist BY c_count
| SORT - custdist, - c_count
```

#### lookup 命令
<a name="supported-ppl-lookup-commands"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

使用 `lookup` 命令，通过添加或替换查询索引（维度表）中的数据，丰富搜索数据。此命令可让您使用维度表中的值扩展索引的字段。您还可以在满足查找条件时使用此命令追加或替换值。使用静态数据集丰富源数据时，`lookup` 命令 `Join` 命令更合适。

**语法**  
使用以下语法：

```
SEARCH source=<sourceIndex>
| <other piped command>
| LOOKUP <lookupIndex> (<lookupMappingField> [AS <sourceMappingField>])...
    [(REPLACE | APPEND) (<inputField> [AS <outputField>])...]
| <other piped command>
```

**lookupIndex**
+ 必需。
+ 查找索引（维度表）的名称。

**lookupMappingField**
+ 必需。
+ 查找索引中的映射键，类似于右表中的联接键。您可以指定以逗号分隔的多个字段。

**sourceMappingField**
+ 可选。
+ 默认：< lookupMappingField >。
+ 源查询中的映射键，类似于左侧的联接键。

**inputField**
+ 可选。
+ 默认：查找索引中可找到匹配值的所有字段。
+ 查找索引中的字段，其中匹配的值将应用于结果输出。您可以指定以逗号分隔的多个字段。

**outputField**
+ 可选。
+ 默认值：`<inputField>`。
+ 输出中的字段。您可以指定多个输出字段。如果在源查询中指定现有字段名称，则其值将替换或附加为 inputField 中的匹配值。如果指定新的字段名称，该名称将被添加到结果中。

**REPLACE \$1 APPEND**
+ 可选。
+ 默认：REPLACE
+ 指定如何处理匹配的值。如果指定 REPLACE，<lookupIndex> 字段中匹配的值会覆盖结果中的值。如果指定 `APPEND`，<lookupIndex> 字段中匹配的值只会追加到结果中的缺失值之后。

**用法**
+ LOOKUP <lookupIndex> id AS cid REPLACE mail AS email
+ LOOKUP <lookupIndex> name REPLACE mail AS email
+ LOOKUP <lookupIndex> id AS cid, name APPEND address, mail AS email
+ LOOKUP <lookupIndex> id

**示例**  
请见以下 示例。

```
SEARCH source=<sourceIndex>
| WHERE orderType = 'Cancelled'
| LOOKUP account_list, mkt_id AS mkt_code REPLACE amount, account_name AS name
| STATS count(mkt_code), avg(amount) BY name
```

```
SEARCH source=<sourceIndex>
| DEDUP market_id
| EVAL category=replace(category, "-", ".")
| EVAL category=ltrim(category, "dvp.")
| LOOKUP bounce_category category AS category APPEND classification
```

```
SEARCH source=<sourceIndex>
| LOOKUP bounce_category category
```

#### parse 命令
<a name="supported-ppl-parse-command"></a>

`parse` 命令使用正则表达式解析文本字段，并将结果附加到搜索结果中。

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

**语法**  
使用以下语法：

```
parse <field> <pattern>    
```

**`field`**
+ 必需。
+ 该字段必须为文本字段。

**`pattern`**
+ 必需的字符串。
+ 这是用于从给定文本字段提取新字段的正则表达式模式。
+ 如果新的字段名称已存在，则会替换原有字段。

**正则表达式**  
正则表达式模式用于通过 Java 正则表达式引擎匹配每个文档的整个文本字段。表达式中的每个命名捕获组都将成为新 `STRING` 字段。

**示例 1：创建新字段**  
该示例说明如何为每个文档创建新字段 `host`。`host` 是 `email` 字段中接在 `@` 之后的主机名。解析 null 字段将返回空字符串。

PPL 查询：

```
os> source=accounts | parse email '.+@(?<host>.+)' | fields email, host ;
fetched rows / total rows = 4/4
+-----------------------+-------------+
| email                 | host        |
|-----------------------+-------------|
| jane_doe@example.com  | example.com |
| john_doe@example.net  | example.net |
| null                  |             |
| juan_li@example.org   | example.org |
+-----------------------+-------------+
```

**示例 2：覆盖现有字段**  
该示例说明如何在移除门牌号的情况下覆盖现有 `address` 字段。

PPL 查询：

```
os> source=accounts | parse address '\d+ (?<address>.+)' | fields address ;
fetched rows / total rows = 4/4
+------------------+
| address          |
|------------------|
| Example Lane     |
| Example Street   |
| Example Avenue   |
| Example Court    |
+------------------+
```

**示例 3：按转换后的解析字段进行筛选和排序**  
该示例说明如何对 `address` 字段中大于 500 的街道号码进行排序。

PPL 查询：

```
os> source=accounts | parse address '(?<streetNumber>\d+) (?<street>.+)' | where cast(streetNumber as int) > 500 | sort num(streetNumber) | fields streetNumber, street ;
fetched rows / total rows = 3/3
+----------------+----------------+
| streetNumber   | street         |
|----------------+----------------|
| ***            | Example Street |
| ***            | Example Avenue |
| 880            | Example Lane   |
+----------------+----------------+
```

**限制**  
parse 命令存在一些限制：
+ 无法再次解析通过 parse 定义的字段。

  以下命令将无法执行：

  ```
  source=accounts | parse address '\d+ (?<street>.+)' | parse street '\w+ (?<road>\w+)'
  ```
+ 通过 parse 定义的字段不能被其他命令覆盖。

  `where` 不会匹配任何文档，因为 `street` 无法覆盖：

  ```
  source=accounts | parse address '\d+ (?<street>.+)' | eval street='1' | where street='1' ;        
  ```
+ parse 使用的文本字段不能被覆盖。

  `address` 无法成功解析，因为 `street` 已被覆盖：

  ```
  source=accounts | parse address '\d+ (?<street>.+)' | eval address='1' ;        
  ```
+ 在 `stats` 命令中使用通过 parse 定义的字段后，无法对其进行筛选或排序。

  以下命令中的 `where` 将无法执行：

  ```
  source=accounts | parse email '.+@(?<host>.+)' | stats avg(age) by host | where host=pyrami.com ;        
  ```

#### patterns 命令
<a name="supported-ppl-patterns-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

`patterns` 命令从文本字段中提取日志模式，并将结果附加到搜索结果中。按日志模式进行分组，便于从海量日志数据中聚合统计信息，从而进行分析和故障排查。

**语法**  
使用以下语法：

```
patterns [new_field=<new-field-name>] [pattern=<pattern>] <field>    
```

**new-field-name**
+ 可选字符串。
+ 这是用于提取模式的新字段名称。
+ 默认值为 `patterns_field`。
+ 如果名称已存在，则会替换原有字段。

**模式**
+ 可选字符串。
+ 这是用于筛选文本字段中不需要字符的正则表达式模式。
+ 如果缺失，则默认模式为字母数字字符（`[a-zA-Z\d]`）。

**字段**
+ 必需。
+ 该字段必须为文本字段。

**示例 1：创建新字段**  
该示例说明如何对每个文档使用 `email` 中的提取标点符号功能。解析 null 字段将返回空字符串。

PPL 查询：

```
os> source=accounts | patterns email | fields email, patterns_field ;
fetched rows / total rows = 4/4
+-----------------------+------------------+
| email                 | patterns_field   |
|-----------------------+------------------|
| jane_doe@example.com  | @.               |
| john_doe@example.net  | @.               |
| null                  |                  |
| juan_li@example.org   | @.               |
+-----------------------+------------------+
```

**示例 2：提取日志模式**  
该示例说明如何使用默认模式从原始日志字段中提取标点符号。

PPL 查询：

```
os> source=apache | patterns message | fields message, patterns_field ;
fetched rows / total rows = 4/4
+-----------------------------------------------------------------------------------------------------------------------------+---------------------------------+
| message                                                                                                                     | patterns_field                  |
|-----------------------------------------------------------------------------------------------------------------------------+---------------------------------|
| 177.95.8.74 - upton5450 [28/Sep/2022:10:15:57 -0700] "HEAD /e-business/mindshare HTTP/1.0" 404 19927                        | ... -  [//::: -] " /-/ /."      |
| ************ - pouros8756 [28/Sep/2022:10:15:57 -0700] "GET /architectures/convergence/niches/mindshare HTTP/1.0" 100 28722 | ... -  [//::: -] " //// /."     |
| *************** - - [28/Sep/2022:10:15:57 -0700] "PATCH /strategize/out-of-the-box HTTP/1.0" 401 27439                      | ... - - [//::: -] " //--- /."   |
| ************** - - [28/Sep/2022:10:15:57 -0700] "POST /users HTTP/1.1" 301 9481                                             | ... - - [//::: -] " / /."       |
+-----------------------------------------------------------------------------------------------------------------------------+---------------------------------+
```

**示例 3：使用自定义正则表达式模式提取日志模式**  
该示例说明如何使用用户定义的模式从原始日志字段中提取标点符号。

PPL 查询：

```
os> source=apache | patterns new_field='no_numbers' pattern='[0-9]' message | fields message, no_numbers ;
fetched rows / total rows = 4/4
+-----------------------------------------------------------------------------------------------------------------------------+--------------------------------------------------------------------------------------+
| message                                                                                                                     | no_numbers                                                                           |
|-----------------------------------------------------------------------------------------------------------------------------+--------------------------------------------------------------------------------------|
| 177.95.8.74 - upton5450 [28/Sep/2022:10:15:57 -0700] "HEAD /e-business/mindshare HTTP/1.0" 404 19927                        | ... - upton [/Sep/::: -] "HEAD /e-business/mindshare HTTP/."                         |
| 127.45.152.6 - pouros8756 [28/Sep/2022:10:15:57 -0700] "GET /architectures/convergence/niches/mindshare HTTP/1.0" 100 28722 | ... - pouros [/Sep/::: -] "GET /architectures/convergence/niches/mindshare HTTP/."   |
| *************** - - [28/Sep/2022:10:15:57 -0700] "PATCH /strategize/out-of-the-box HTTP/1.0" 401 27439                      | ... - - [/Sep/::: -] "PATCH /strategize/out-of-the-box HTTP/."                       |
| ************** - - [28/Sep/2022:10:15:57 -0700] "POST /users HTTP/1.1" 301 9481                                             | ... - - [/Sep/::: -] "POST /users HTTP/."                                            |
+-----------------------------------------------------------------------------------------------------------------------------+--------------------------------------------------------------------------------------+
```

**限制**  
patterns 命令与 parse 命令具有相同的限制。

#### rare 命令
<a name="supported-ppl-rare-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

使用 `rare` 命令查找字段列表中所有字段的最不常见值。

**注意**  
对于每个分组字段值的唯一元组，最多返回 10 个结果。

**语法**  
使用以下语法：

```
rare [N] <field-list> [by-clause] rare_approx [N] <field-list> [by-clause]
```

**field-list**
+ 必需。
+ 以逗号分隔的字段名称列表。

**by-clause**
+ 可选。
+ 用于对结果进行分组的一个或多个字段。

**N**
+ 要返回的结果数量。
+ 默认值：10

**rare\$1approx**
+ 使用 [ HyperLogLog\$1\$1 算法估计的基数计算稀有 (n) 个字段的](https://spark.apache.org/docs/latest/sql-ref-functions-builtin.html)近似计数。

**示例 1：查找字段中最不常见值**  
该示例查找所有账户中有关性别的最不常见值。

PPL 查询：

```
os> source=accounts | rare gender;
os> source=accounts | rare_approx 10 gender;
os> source=accounts | rare_approx gender;
fetched rows / total rows = 2/2
+----------+
| gender   |
|----------|
| F        |
| M        |
+----------+
```

**示例 2：按性别分类查找最不常见值**  
该示例按性别分类查找所有账户组中有关年龄的最不常见值。

PPL 查询：

```
os> source=accounts | rare 5 age by gender;
os> source=accounts | rare_approx 5 age by gender;
fetched rows / total rows = 4/4
+----------+-------+
| gender   | age   |
|----------+-------|
| F        | 28    |
| M        | 32    |
| M        | 33    |
| M        | 36    |
+----------+-------+
```

#### rename 命令
<a name="supported-ppl-rename-command"></a>

使用 `rename` 命令，更改搜索结果中一个或多个字段的名称。

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

**语法**  
使用以下语法：

```
rename <source-field> AS <target-field>["," <source-field> AS <target-field>]...    
```

**source-field**
+ 必需。
+ 这是您想要重命名的字段名称。

**target-field**
+ 必需。
+ 这是您想要重命名的名称。

**示例 1：重命名一个字段**  
此示例说明如何重命名单个字段。

PPL 查询：

```
os> source=accounts | rename account_number as an | fields an;
fetched rows / total rows = 4/4
+------+
| an   |
|------|
| 1    |
| 6    |
| 13   |
| 18   |
+------+
```

**示例 2：重命名多个字段**  
此示例说明如何重命名多个字段。

PPL 查询：

```
os> source=accounts | rename account_number as an, employer as emp | fields an, emp;
fetched rows / total rows = 4/4
+------+---------+
| an   | emp     |
|------+---------|
| 1    | Pyrami  |
| 6    | Netagy  |
| 13   | Quility |
| 18   | null    |
+------+---------+
```

**限制**
+ 不支持覆盖现有字段：

  ```
  source=accounts | grok address '%{NUMBER} %{GREEDYDATA:address}' | fields address        
  ```

#### search 命令
<a name="supported-ppl-search-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

使用 `search` 命令，从索引中检索文档。`search` 命令仅可用作 PPL 查询中的第一个命令。

**语法**  
使用以下语法：

```
search source=[<remote-cluster>:]<index> [boolean-expression]    
```

**搜索**
+ 可选。
+ 搜索关键词，可省略。

**索引**
+ 必需。
+ 搜索命令必须指定从哪个索引进行查询。
+ 对于跨集群搜索，索引名称可以加上前缀 `<cluster name>:`。

**bool-expression**
+ 可选。
+ 计算结果为布尔值的任何表达式。

**示例 1：提取所有数据**  
该示例展示从账户索引中提取所有文档。

PPL 查询：

```
os> source=accounts;
+------------------+-------------+----------------------+-----------+----------+--------+----------------+---------+-------+-----------------------+------------+
| account_number   | firstname   | address              | balance   | gender   | city   | employer       | state   | age   | email                 | lastname   |
|------------------+-------------+----------------------+-----------+----------+--------+----------------+---------+-------+-----------------------+------------|
| 1                | Jorge       | *** Any Lane         | 39225     | M        | Brogan | ExampleCorp    | IL      | 32    | jane_doe@example.com  | Souza      |
| 6                | John        | *** Example Street   | 5686      | M        | Dante  | AnyCorp        | TN      | 36    | john_doe@example.com  | Doe        |
| 13               | Jane        | *** Any Street       | *****     | F        | Nogal  | ExampleCompany | VA      | 28    | null                  | Doe        |
| 18               | Juan        | *** Example Court    | 4180      | M        | Orick  | null           | MD      | 33    | juan_li@example.org   | Li         |
+------------------+-------------+----------------------+-----------+----------+--------+----------------+---------+-------+-----------------------+------------+
```

**示例 2：使用条件提取数据**  
该示例展示使用 从账户索引中提取所有文档。

PPL 查询：

```
os> SEARCH source=accounts account_number=1 or gender="F";
+------------------+-------------+--------------------+-----------+----------+--------+----------------+---------+-------+-------------------------+------------+
| account_number   | firstname   | address            | balance   | gender   | city   | employer       | state   | age   | email                -  | lastname   |
|------------------+-------------+--------------------+-----------+----------+--------+----------------+---------+-------+-------------------------+------------|
| 1                | Jorge       | *** Any Lane       | *****     | M        | Brogan | ExampleCorp    | IL      | 32    | jorge_souza@example.com | Souza      |
| 13               | Jane        | *** Any Street     | *****     | F        | Nogal  | ExampleCompany | VA      | 28    | null                    | Doe        |
+------------------+-------------+--------------------+-----------+----------+--------+-----------------+---------+-------+------------------------+------------+
```

#### sort 命令
<a name="supported-ppl-sort-command"></a>

使用 `sort` 命令，按指定字段对搜索结果进行排序。

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

**语法**  
使用以下语法：

```
sort <[+|-] sort-field>...
```

**[\$1\$1-]**
+ 可选。
+ 加号 [\$1] 代表升序， NULL/MISSING 值在前。
+ 减号 [-] 代表降序， NULL/MISSING 值排在最后。
+ 默认：升序排序， NULL/MISSING 值在前。

**sort-field**
+ 必需。
+ 用于排序的字段。

**示例 1：按一个字段排序**  
该示例说明如何根据年龄字段按升序对文档进行排序。

PPL 查询：

```
os> source=accounts | sort age | fields account_number, age;
fetched rows / total rows = 4/4
+------------------+-------+
| account_number   | age   |
|------------------+-------|
| 13               | 28    |
| 1                | 32    |
| 18               | 33    |
| 6                | 36    |
+------------------+-------+
```

**示例 2：按一个字段排序并返回所有结果**  
该示例说明如何根据年龄字段按升序对文档进行排序。

PPL 查询：

```
os> source=accounts | sort age | fields account_number, age;
fetched rows / total rows = 4/4
+------------------+-------+
| account_number   | age   |
|------------------+-------|
| 13               | 28    |
| 1                | 32    |
| 18               | 33    |
| 6                | 36    |
+------------------+-------+
```

**示例 3：按一个字段降序排序**  
该示例说明如何根据年龄字段按降序对文档进行排序。

PPL 查询：

```
os> source=accounts | sort - age | fields account_number, age;
fetched rows / total rows = 4/4
+------------------+-------+
| account_number   | age   |
|------------------+-------|
| 6                | 36    |
| 18               | 33    |
| 1                | 32    |
| 13               | 28    |
+------------------+-------+
```

**示例 4：按多个字段排序**  
该示例说明如何对文档进行排序，性别字段按升序排序，同时年龄字段按降序排序。

PPL 查询：

```
os> source=accounts | sort + gender, - age | fields account_number, gender, age;
fetched rows / total rows = 4/4
+------------------+----------+-------+
| account_number   | gender   | age   |
|------------------+----------+-------|
| 13               | F        | 28    |
| 6                | M        | 36    |
| 18               | M        | 33    |
| 1                | M        | 32    |
+------------------+----------+-------+
```

**示例 5：按包含 null 值的字段排序**  
该示例说明如何按默认选项（升序排序，null 值置于首位）对雇主字段进行排序。结果显示 null 值位于第一行。

PPL 查询：

```
os> source=accounts | sort employer | fields employer;
fetched rows / total rows = 4/4
+------------+
| employer   |
|------------|
| null       |
| AnyCompany |
| AnyCorp    |
| AnyOrgty   |
+------------+
```

#### stats 命令
<a name="supported-ppl-stats-command"></a>

使用 `stats` 命令，根据搜索结果计算聚合。

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

**NULL/MISSING 值处理**  



**NULL/MISSING 值处理**  

| 函数 | NULL | 缺失 | 
| --- | --- | --- | 
| COUNT | 未计数 | 未计数 | 
| SUM | 忽略 | 忽略 | 
| AVG | 忽略 | 忽略 | 
| MAX | 忽略 | 忽略 | 
| MIN | 忽略 | 忽略 | 

**语法**  
使用以下语法：

```
stats <aggregation>... [by-clause]    
```

**聚合**
+ 必需。
+ 应用于字段的聚合函数。

**by-clause**
+ 可选。
+ 语法：`by [span-expression,] [field,]...`
+ 指定对聚合结果进行分组的字段和表达式。by 子句允许您使用字段和表达式对聚合结果进行分组。您可以使用标量函数、聚合函数甚至跨度表达式，将特定字段拆分为间隔相等的存储桶。
+ 默认：如果未指定 `<by-clause>`，则 stats 命令返回单行，表示对整个结果集进行聚合。

**span-expression**  

+ 可选，最多一个。
+ 语法：`span(field_expr, interval_expr)`
+ 默认情况下，间隔表达式的单位为自然单位。如果该字段是日期和时间类型字段，并且间隔以 date/time 单位表示，则可以在间隔表达式中指定单位。
+ 例如，按照 10 年为单位将 `age` 字段拆分为存储桶，如 `span(age, 10)` 所示。要将时间戳字段拆分为每小时间隔，请使用 `span(timestamp, 1h)`。


**可用时间单位**  

| 跨度单位 | 
| --- | 
| 毫秒（ms） | 
| 秒（s） | 
| 分钟（m，区分大小写） | 
| 小时（h） | 
| 天（d） | 
| 周（w） | 
| 月（M，区分大小写） | 
| 季度（q） | 
| 年（y） | 

**聚合函数**  


**`COUNT`**  
返回 SELECT 语句检索到的行中 expr 出现的次数。

示例：

```
os> source=accounts | stats count();
fetched rows / total rows = 1/1
+-----------+
| count()   |
|-----------|
| 4         |
+-----------+
```

**`SUM`**  
使用 `SUM(expr)`，返回 expr 的总和。

示例

```
os> source=accounts | stats sum(age) by gender;
fetched rows / total rows = 2/2
+------------+----------+
| sum(age)   | gender   |
|------------+----------|
| 28         | F        |
| 101        | M        |
+------------+----------+
```

**`AVG`**  
使用 `AVG(expr)`，返回 expr 的平均值。

示例

```
os> source=accounts | stats avg(age) by gender;
fetched rows / total rows = 2/2
+--------------------+----------+
| avg(age)           | gender   |
|--------------------+----------|
| 28.0               | F        |
| 33.666666666666664 | M        |
+--------------------+----------+
```

**`MAX`**  
使用 `MAX(expr)`，返回 expr 的最大值。

示例

```
os> source=accounts | stats max(age);
fetched rows / total rows = 1/1
+------------+
| max(age)   |
|------------|
| 36         |
+------------+
```

**`MIN`**  
使用 `MIN(expr)`，返回 expr 的最小值。

示例

```
os> source=accounts | stats min(age);
fetched rows / total rows = 1/1
+------------+
| min(age)   |
|------------|
| 28         |
+------------+
```

**`STDDEV_SAMP`**  
使用 `STDDEV_SAMP(expr)`，返回 expr 的样本标准差。

示例：

```
os> source=accounts | stats stddev_samp(age);
fetched rows / total rows = 1/1
+--------------------+
| stddev_samp(age)   |
|--------------------|
| 3.304037933599835  |
+--------------------+
```

**STDDEV\$1POP**  
使用 `STDDEV_POP(expr)`，返回 expr 的总体标准差。

示例：

```
os> source=accounts | stats stddev_pop(age);
fetched rows / total rows = 1/1
+--------------------+
| stddev_pop(age)    |
|--------------------|
| 2.**************** |
+--------------------+
```

**TAKE**  
使用 `TAKE(field [, size])`，返回字段的原始值。无法保证值的顺序。

**字段**
+ 必需。
+ 该字段必须为文本字段。

**size**
+ 可选整数。
+ 应返回值的数量。
+ 默认值为 10。

**示例**  


```
os> source=accounts | stats take(firstname);
fetched rows / total rows = 1/1
+-----------------------------+
| take(firstname)             |
|-----------------------------|
| [Jane, Mary, Nikki, Juan    |
+-----------------------------+
```

**PERCENTILE 或 PERCENTILE\$1APPROX**  
使用 `PERCENTILE(expr, percent)` 或 `PERCENTILE_APPROX(expr, percent)`，返回 expr 在指定百分比处的近似百分位数值。

**百分比**
+ 该数值必须是 0 到 100 之间的常数。

**示例**  


```
os> source=accounts | stats percentile(age, 90) by gender;
fetched rows / total rows = 2/2
+-----------------------+----------+
| percentile(age, 90)   | gender   |
|-----------------------+----------|
| 28                    | F        |
| 36                    | M        |
+-----------------------+----------+
```

**示例 1：计算事件计数**  
该示例说明如何计算账户中的事件计数。

```
os> source=accounts | stats count();
fetched rows / total rows = 1/1
+-----------+
| count()   |
|-----------|
| 4         |
+-----------+
```

**示例 2：计算字段的平均值**  
该示例说明如何计算所有账户的平均年龄。

```
os> source=accounts | stats avg(age);
fetched rows / total rows = 1/1
+------------+
| avg(age)   |
|------------|
| 32.25      |
+------------+
```

**示例 3：按组计算字段的平均值**  
该示例说明如何按性别分组计算所有账户的平均年龄。

```
os> source=accounts | stats avg(age) by gender;
fetched rows / total rows = 2/2
+--------------------+----------+
| avg(age)           | gender   |
|--------------------+----------|
| 28.0               | F        |
| 33.666666666666664 | M        |
+--------------------+----------+
```

**示例 4：按组计算字段的平均值、总和及计数**  
该示例说明如何按性别分组计算所有账户的平均年龄、总年龄和事件计数。

```
os> source=accounts | stats avg(age), sum(age), count() by gender;
fetched rows / total rows = 2/2
+--------------------+------------+-----------+----------+
| avg(age)           | sum(age)   | count()   | gender   |
|--------------------+------------+-----------+----------|
| 28.0               | 28         | 1         | F        |
| 33.666666666666664 | 101        | 3         | M        |
+--------------------+------------+-----------+----------+
```

**示例 5：计算字段的最大值**  
该示例计算所有账户的最大年龄。

```
os> source=accounts | stats max(age);
fetched rows / total rows = 1/1
+------------+
| max(age)   |
|------------|
| 36         |
+------------+
```

**示例 6：按组计算字段的最大值和最小值**  
该示例按性别分组计算所有账户的最大年龄值和最小年龄值。

```
os> source=accounts | stats max(age), min(age) by gender;
fetched rows / total rows = 2/2
+------------+------------+----------+
| max(age)   | min(age)   | gender   |
|------------+------------+----------|
| 28         | 28         | F        |
| 36         | 32         | M        |
+------------+------------+----------+
```

**示例 7：计算字段的不同计数**  
要获取字段中不同值的计数，可使用 `DISTINCT_COUNT`（或 `DC`）函数而不是 `COUNT`。该示例计算所有账户中性别字段的总计数和独立计数。

```
os> source=accounts | stats count(gender), distinct_count(gender);
fetched rows / total rows = 1/1
+-----------------+--------------------------+
| count(gender)   | distinct_count(gender)   |
|-----------------+--------------------------|
| 4               | 2                        |
+-----------------+--------------------------+
```

**示例 8：按跨度计算计数**  
该示例以 10 年为间隔统计年龄计数。

```
os> source=accounts | stats count(age) by span(age, 10) as age_span
fetched rows / total rows = 2/2
+--------------+------------+
| count(age)   | age_span   |
|--------------+------------|
| 1            | 20         |
| 3            | 30         |
+--------------+------------+
```

**示例 9：按性别和跨度计算计数**  
此示例统计按性别分组且年龄跨度为 5 年的记录数。

```
os> source=accounts | stats count() as cnt by span(age, 5) as age_span, gender
fetched rows / total rows = 3/3
+-------+------------+----------+
| cnt   | age_span   | gender   |
|-------+------------+----------|
| 1     | 25         | F        |
| 2     | 30         | M        |
| 1     | 35         | M        |
+-------+------------+----------+
```

span 表达式始终作为第一个分组键出现，无论命令中指定的顺序如何。

```
os> source=accounts | stats count() as cnt by gender, span(age, 5) as age_span
fetched rows / total rows = 3/3
+-------+------------+----------+
| cnt   | age_span   | gender   |
|-------+------------+----------|
| 1     | 25         | F        |
| 2     | 30         | M        |
| 1     | 35         | M        |
+-------+------------+----------+
```

**示例 10：计算计数并获取按性别和跨度划分的电子邮件列表**  
该示例以 10 年为间隔统计年龄计数，并按性别进行分组，每行获得最多 5 封电子邮件的列表。

```
os> source=accounts | stats count() as cnt, take(email, 5) by span(age, 5) as age_span, gender
fetched rows / total rows = 3/3
+-------+----------------------------------------------------+------------+----------+
| cnt   | take(email, 5)                                     | age_span   | gender   |
|-------+----------------------------------------------------+------------+----------|
| 1     | []                                                 | 25         | F        |
| 2     | [janedoe@anycompany.com,juanli@examplecompany.org] | 30         | M        |
| 1     | [marymajor@examplecorp.com]                        | 35         | M        |
+-------+----------------------------------------------------+------------+----------+
```

**示例 11：计算字段的百分位数**  
该示例说明如何计算所有账户的第 90 百分位年龄值。

```
os> source=accounts | stats percentile(age, 90);
fetched rows / total rows = 1/1
+-----------------------+
| percentile(age, 90)   |
|-----------------------|
| 36                    |
+-----------------------+
```

**示例 12：按组计算字段的百分位数**  
该示例说明如何按性别分组计算所有账户的第 90 百分位年龄值。

```
os> source=accounts | stats percentile(age, 90) by gender;
fetched rows / total rows = 2/2
+-----------------------+----------+
| percentile(age, 90)   | gender   |
|-----------------------+----------|
| 28                    | F        |
| 36                    | M        |
+-----------------------+----------+
```

**示例 13：按性别和跨度计算百分位数**  
该示例按 10 年为间隔，并按性别分组，统计第 90 百分位年龄值。

```
os> source=accounts | stats percentile(age, 90) as p90 by span(age, 10) as age_span, gender
fetched rows / total rows = 2/2
+-------+------------+----------+
| p90   | age_span   | gender   |
|-------+------------+----------|
| 28    | 20         | F        |
| 36    | 30         | M        |
+-------+------------+----------+
```

```
- `source = table | stats avg(a) `
- `source = table | where a < 50 | stats avg(c) `
- `source = table | stats max(c) by b`
- `source = table | stats count(c) by b | head 5`
- `source = table | stats distinct_count(c)`
- `source = table | stats stddev_samp(c)`
- `source = table | stats stddev_pop(c)`
- `source = table | stats percentile(c, 90)`
- `source = table | stats percentile_approx(c, 99)`
```

**带跨度聚合**  


```
- `source = table  | stats count(a) by span(a, 10) as a_span`
- `source = table  | stats sum(age) by span(age, 5) as age_span | head 2`
- `source = table  | stats avg(age) by span(age, 20) as age_span, country  | sort - age_span |  head 2`
```

**具有时间窗口跨度的聚合（翻转窗口函数）**  


```
- `source = table | stats sum(productsAmount) by span(transactionDate, 1d) as age_date | sort age_date`
- `source = table | stats sum(productsAmount) by span(transactionDate, 1w) as age_date, productId`
```

**按多个级别对聚合分组**  


```
- `source = table | stats avg(age) as avg_state_age by country, state | stats avg(avg_state_age) as avg_country_age by country`
- `source = table | stats avg(age) as avg_city_age by country, state, city | eval new_avg_city_age = avg_city_age - 1 | stats avg(new_avg_city_age) as avg_state_age by country, state | where avg_state_age > 18 | stats avg(avg_state_age) as avg_adult_country_age by country`
```

#### subquery 命令
<a name="supported-ppl-subquery-commands"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

使用 `subquery` 命令，在管道处理语言（PPL）语句中执行复杂的嵌套查询。

```
source=logs | where field in [ subquery source=events | where condition | fields field ]
```

在此示例中，主搜索（`source=logs`）按子查询（`source=events`）的结果进行筛选。

subquery 命令支持用于复杂数据分析的多层嵌套。

**嵌套子查询示例**  


```
source=logs | where id in [ subquery source=users | where user in [ subquery source=actions | where action="login" | fields user] | fields uid ]  
```

**InSubquery 用法**
+ `source = outer | where a in [ source = inner | fields b ]`
+ `source = outer | where (a) in [ source = inner | fields b ]`
+ `source = outer | where (a,b,c) in [ source = inner | fields d,e,f ]`
+ `source = outer | where a not in [ source = inner | fields b ]`
+ `source = outer | where (a) not in [ source = inner | fields b ]`
+ `source = outer | where (a,b,c) not in [ source = inner | fields d,e,f ]`
+ `source = outer a in [ source = inner | fields b ]`（使用子查询进行搜索筛选）
+ `source = outer a not in [ source = inner | fields b ]`（使用子查询进行搜索筛选）
+ `source = outer | where a in [ source = inner1 | where b not in [ source = inner2 | fields c ] | fields b ]`（嵌套）
+ `source = table1 | inner join left = l right = r on l.a = r.a AND r.a in [ source = inner | fields d ] | fields l.a, r.a, b, c`（作为联接筛选器）

**使用 IN-Subquery PPL 的 SQL 迁移示例**  
TPC-H Q4（带聚合的 in-subquery）

```
select
  o_orderpriority,
  count(*) as order_count
from
  orders
where
  o_orderdate >= date '1993-07-01'
  and o_orderdate < date '1993-07-01' + interval '3' month
  and o_orderkey in (
    select
      l_orderkey
    from
      lineitem
    where l_commitdate < l_receiptdate
  )
group by
  o_orderpriority
order by
  o_orderpriority
```

由 PPL InSubquery 查询重写：

```
source = orders
| where o_orderdate >= "1993-07-01" and o_orderdate < "1993-10-01" and o_orderkey IN
  [ source = lineitem
    | where l_commitdate < l_receiptdate
    | fields l_orderkey
  ]
| stats count(1) as order_count by o_orderpriority
| sort o_orderpriority
| fields o_orderpriority, order_count
```

TPC-H Q20（嵌套的 in-subquery）

```
select
  s_name,
  s_address
from
  supplier,
  nation
where
  s_suppkey in (
    select
      ps_suppkey
    from
      partsupp
    where
      ps_partkey in (
        select
          p_partkey
        from
          part
        where
          p_name like 'forest%'
      )
  )
  and s_nationkey = n_nationkey
  and n_name = 'CANADA'
order by
  s_name
```

由 PPL InSubquery 查询重写：

```
source = supplier
| where s_suppkey IN [
    source = partsupp
    | where ps_partkey IN [
        source = part
        | where like(p_name, "forest%")
        | fields p_partkey
      ]
    | fields ps_suppkey
  ]
| inner join left=l right=r on s_nationkey = n_nationkey and n_name = 'CANADA'
  nation
| sort s_name
```

**ExistsSubquery 用法**  
假设：`a`、`b` 是表 outer 的字段，`c`、`d` 是表 inner 的字段，`e`、`f`是表 inner2 的字段。
+ `source = outer | where exists [ source = inner | where a = c ]`
+ `source = outer | where not exists [ source = inner | where a = c ]`
+ `source = outer | where exists [ source = inner | where a = c and b = d ]`
+ `source = outer | where not exists [ source = inner | where a = c and b = d ]`
+ `source = outer exists [ source = inner | where a = c ]`（使用子查询进行搜索筛选）
+ `source = outer not exists [ source = inner | where a = c ]`（使用子查询进行搜索筛选）
+ `source = table as t1 exists [ source = table as t2 | where t1.a = t2.a ]`（表别名在 exists 子查询中大有助益）
+ `source = outer | where exists [ source = inner1 | where a = c and exists [ source = inner2 | where c = e ] ]`（嵌套）
+ `source = outer | where exists [ source = inner1 | where a = c | where exists [ source = inner2 | where c = e ] ]`（嵌套）
+ `source = outer | where exists [ source = inner | where c > 10 ]`（不相关的 exists）
+ `source = outer | where not exists [ source = inner | where c > 10 ]`（不相关的 exists）
+ `source = outer | where exists [ source = inner ] | eval l = "nonEmpty" | fields l`（特殊的不相关 exists）

**ScalarSubquery 用法**  
假设：`a`、`b` 是表 outer 的字段，`c`、`d` 是表 inner 的字段，`e`、`f`是表 nested 的字段。

**不相关的标量子查询**  
在 Select 中：
+ `source = outer | eval m = [ source = inner | stats max(c) ] | fields m, a`
+ `source = outer | eval m = [ source = inner | stats max(c) ] + b | fields m, a`

在 Where 中：
+ `source = outer | where a > [ source = inner | stats min(c) ] | fields a`

在搜索筛选条件中：
+ `source = outer a > [ source = inner | stats min(c) ] | fields a`

**相关的标量子查询**  
在 Select 中：
+ `source = outer | eval m = [ source = inner | where outer.b = inner.d | stats max(c) ] | fields m, a`
+ `source = outer | eval m = [ source = inner | where b = d | stats max(c) ] | fields m, a`
+ `source = outer | eval m = [ source = inner | where outer.b > inner.d | stats max(c) ] | fields m, a`

在 Where 中：
+ `source = outer | where a = [ source = inner | where outer.b = inner.d | stats max(c) ]`
+ `source = outer | where a = [ source = inner | where b = d | stats max(c) ]`
+ `source = outer | where [ source = inner | where outer.b = inner.d OR inner.d = 1 | stats count() ] > 0 | fields a`

在搜索筛选条件中：
+ `source = outer a = [ source = inner | where b = d | stats max(c) ]`
+ `source = outer [ source = inner | where outer.b = inner.d OR inner.d = 1 | stats count() ] > 0 | fields a`

**嵌套的标量子查询**  

+ `source = outer | where a = [ source = inner | stats max(c) | sort c ] OR b = [ source = inner | where c = 1 | stats min(d) | sort d ]`
+ `source = outer | where a = [ source = inner | where c = [ source = nested | stats max(e) by f | sort f ] | stats max(d) by c | sort c | head 1 ]`

**（关系）子查询**  
`InSubquery`、`ExistsSubquery` 和 `ScalarSubquery` 都是子查询表达式。但 `RelationSubquery` 不是子查询表达式，而是子查询执行计划，常用于 Join 子句或 From 子句。
+ `source = table1 | join left = l right = r [ source = table2 | where d > 10 | head 5 ]`（右联接侧中的子查询）
+ `source = [ source = table1 | join left = l right = r [ source = table2 | where d > 10 | head 5 ] | stats count(a) by b ] as outer | head 1`

**其他上下文**  
`InSubquery`、`ExistsSubquery`、和 `ScalarSubquery` 是 `where` 子句和搜索筛选条件中常用的子查询表达式。

Where 命令：

```
| where <boolean expression> | ...    
```

搜索筛选条件：

```
search source=* <boolean expression> | ...    
```

子查询表达式可用于布尔表达式中：

```
| where orders.order_id in [ source=returns | where return_reason="damaged" | field order_id ]    
```

`orders.order_id in [ source=... ]` 是 `<boolean expression>`。

通常，我们将这种子查询子句命名为 `InSubquery` 表达式。这是 `<boolean expression>`。

**具有不同联接类型的子查询**  
使用 `ScalarSubquery` 的示例：

```
source=employees
| join source=sales on employees.employee_id = sales.employee_id
| where sales.sale_amount > [ source=targets | where target_met="true" | fields target_value ]
```

与 InSubquery ExistsSubquery、和 ScalarSubquery，a RelationSubquery 不是子查询表达式。而是子查询计划。

```
SEARCH source=customer
| FIELDS c_custkey
| LEFT OUTER JOIN left = c, right = o ON c.c_custkey = o.o_custkey
   [
      SEARCH source=orders
      | WHERE o_comment NOT LIKE '%unusual%packages%'
      | FIELDS o_orderkey, o_custkey
   ]
| STATS ...
```

#### top 命令
<a name="supported-ppl-top-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

使用 `top` 命令查找字段列表中所有字段的最常见值。

**语法**  
使用以下语法：

```
top [N] <field-list> [by-clause] top_approx [N] <field-list> [by-clause]
```

**N**
+ 要返回的结果数量。
+ 默认值：10

**field-list**
+ 必需。
+ 以逗号分隔的字段名称列表。

**by-clause**
+ 可选。
+ 用于对结果进行分组的一个或多个字段。

**top\$1approx**
+ 使用 [ HyperLogLog\$1\$1 估计的基数算法对 (n) 个顶部字段的近似计数](https://spark.apache.org/docs/latest/sql-ref-functions-builtin.html)。

**示例 1：查找字段中最常见值**  
该示例查找所有账户中有关性别的最常见值。

PPL 查询：

```
os> source=accounts | top gender;
os> source=accounts | top_approx gender;
fetched rows / total rows = 2/2
+----------+
| gender   |
|----------|
| M        |
| F        |
+----------+
```

**示例 2：查找字段中最常见值（限制为 1）**  
该示例查找所有账户中单一性别的最常见值。

PPL 查询：

```
os> source=accounts | top_approx 1 gender;
fetched rows / total rows = 1/1
+----------+
| gender   |
|----------|
| M        |
+----------+
```

**示例 3：查找按性别分组的最常见值**  
该示例查找所有账户按性别分组的最常见的年龄值。

PPL 查询：

```
os> source=accounts | top 1 age by gender;
os> source=accounts | top_approx 1 age by gender;
fetched rows / total rows = 2/2
+----------+-------+
| gender   | age   |
|----------+-------|
| F        | 28    |
| M        | 32    |
+----------+-------+
```

#### trendline 命令
<a name="supported-ppl-trendline-commands"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

使用 `trendline` 命令，计算字段的移动平均值。

**语法**  
使用以下语法

```
TRENDLINE [sort <[+|-] sort-field>] SMA(number-of-datapoints, field) [AS alias] [SMA(number-of-datapoints, field) [AS alias]]... 
```

**[\$1\$1-]**
+ 可选。
+ 加号 [\$1] 代表升序， NULL/MISSING 值在前。
+ 减号 [-] 代表降序， NULL/MISSING 值排在最后。
+ 默认：升序排序， NULL/MISSING 值在前。

**sort-field**
+ 使用排序时必须指定。
+ 用于排序的字段。

**number-of-datapoints**
+ 必需。
+ 用于计算移动平均线的数据点数。
+ 必须大于 0。

**字段**
+ 必需。
+ 应计算移动平均线的字段名称。

**别名**
+ 可选。
+ 包含移动平均线的生成列名称。

仅支持简单移动平均（SMA）类型。计算方式如下：

```
f[i]: The value of field 'f' in the i-th data-point
n: The number of data-points in the moving window (period)
t: The current time index

SMA(t) = (1/n) * Σ(f[i]), where i = t-n+1 to t
```

**示例 1：计算温度时间序列的简单移动平均**  
该示例使用两个数据点计算温度的简单移动平均。

PPL 查询：

```
os> source=t | trendline sma(2, temperature) as temp_trend;
fetched rows / total rows = 5/5
+-----------+---------+--------------------+----------+
|temperature|device-id|           timestamp|temp_trend|
+-----------+---------+--------------------+----------+
|         12|     1492|2023-04-06 17:07:...|      NULL|
|         12|     1492|2023-04-06 17:07:...|      12.0|
|         13|      256|2023-04-06 17:07:...|      12.5|
|         14|      257|2023-04-06 17:07:...|      13.5|
|         15|      258|2023-04-06 17:07:...|      14.5|
+-----------+---------+--------------------+----------+
```

**示例 2：计算排序后温度时间序列的简单移动平均**  
该示例使用按 device-id 降序排列的两个和三个数据点，计算温度的两个简单移动平均。

PPL 查询：

```
os> source=t | trendline sort - device-id sma(2, temperature) as temp_trend_2 sma(3, temperature) as temp_trend_3;
fetched rows / total rows = 5/5
+-----------+---------+--------------------+------------+------------------+
|temperature|device-id|           timestamp|temp_trend_2|      temp_trend_3|
+-----------+---------+--------------------+------------+------------------+
|         15|      258|2023-04-06 17:07:...|        NULL|              NULL|
|         14|      257|2023-04-06 17:07:...|        14.5|              NULL|
|         13|      256|2023-04-06 17:07:...|        13.5|              14.0|
|         12|     1492|2023-04-06 17:07:...|        12.5|              13.0|
|         12|     1492|2023-04-06 17:07:...|        12.0|12.333333333333334|
+-----------+---------+--------------------+------------+------------------+
```

#### where 命令
<a name="supported-ppl-where-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

`where` 命令使用 bool-expression 筛选搜索结果。仅当 bool-expression 的计算结果为 true 时，才返回结果。

**语法**  
使用以下语法：

```
where <boolean-expression>    
```

**bool-expression**
+ 可选。
+ 任何可计算为布尔值的表达式。

**示例 1：使用条件筛选结果集**  
该示例说明如何从账户索引中提取满足特定条件的文档。

PPL 查询：

```
os> source=accounts | where account_number=1 or gender="F" | fields account_number, gender;
fetched rows / total rows = 2/2
+------------------+----------+
| account_number   | gender   |
|------------------+----------|
| 1                | M        |
| 13               | F        |
+------------------+----------+
```

**其他示例**  


**具有逻辑条件的筛选器**
+ `source = table | where c = 'test' AND a = 1 | fields a,b,c`
+ `source = table | where c != 'test' OR a > 1 | fields a,b,c | head 1`
+ `source = table | where c = 'test' NOT a > 1 | fields a,b,c`
+ `source = table | where a = 1 | fields a,b,c`
+ `source = table | where a >= 1 | fields a,b,c`
+ `source = table | where a < 1 | fields a,b,c`
+ `source = table | where b != 'test' | fields a,b,c`
+ `source = table | where c = 'test' | fields a,b,c | head 3`
+ `source = table | where ispresent(b)`
+ `source = table | where isnull(coalesce(a, b)) | fields a,b,c | head 3`
+ `source = table | where isempty(a)`
+ `source = table | where isblank(a)`
+ `source = table | where case(length(a) > 6, 'True' else 'False') = 'True'`
+ `source = table | where a between 1 and 4`：注意：这将返回 >= 1 和 <= 4，即 [1, 4]
+ `source = table | where b not between '2024-09-10' and '2025-09-10'`：注意：这将返回 b >= '\$1\$1\$1\$1\$1\$1\$1\$1\$1\$1 '和 b <=' 2025-09-10 '
+ `source = table | where cidrmatch(ip, '***********/24')`
+ `source = table | where cidrmatch(ipv6, '2003:db8::/32')`

```
source = table | eval status_category =
    case(a >= 200 AND a < 300, 'Success',
    a >= 300 AND a < 400, 'Redirection',
    a >= 400 AND a < 500, 'Client Error',
    a >= 500, 'Server Error'
    else 'Incorrect HTTP status code')
    | where case(a >= 200 AND a < 300, 'Success',
    a >= 300 AND a < 400, 'Redirection',
    a >= 400 AND a < 500, 'Client Error',
    a >= 500, 'Server Error'
    else 'Incorrect HTTP status code'
    ) = 'Incorrect HTTP status code'
```

```
source = table
    | eval factor = case(a > 15, a - 14, isnull(b), a - 7, a < 3, a + 1 else 1)
    | where case(factor = 2, 'even', factor = 4, 'even', factor = 6, 'even', factor = 8, 'even' else 'odd') = 'even'
    |  stats count() by factor
```

#### 字段摘要
<a name="supported-ppl-field-summary-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 命令，请参阅。[命令](#supported-ppl-commands)

使用 `fieldsummary` 命令，计算每个字段的基本统计数据（计数、唯一值计数、最小值、最大值、平均值、标准差、平均值），并确定每个字段的数据类型。此命令可与任何前置管道配合使用，并会将其纳入处理范围。

**语法**  
使用下面的语法。对于 CloudWatch 日志用例，查询中仅支持一个字段。

```
... | fieldsummary <field-list> (nulls=true/false)
```

**includefields**
+ 需收集统计信息的全部列表，最终整合为统一的结果集。

**null**
+ 可选。
+  如果设置为 true，则在聚合计算中包含 null 值（对于数值类型，将 null 替换为零）。

**示例 1**  
PPL 查询：

```
os> source = t | where status_code != 200 | fieldsummary includefields= status_code nulls=true
+------------------+-------------+------------+------------+------------+------------+------------+------------+----------------|
| Fields           | COUNT       | COUNT_DISTINCT    |  MIN  |  MAX   |  AVG   |  MEAN   |        STDDEV       | NUlls | TYPEOF |
|------------------+-------------+------------+------------+------------+------------+------------+------------+----------------|
| "status_code"    |      2      |         2         | 301   |   403  |  352.0 |  352.0  |  72.12489168102785  |  0    | "int"  |
+------------------+-------------+------------+------------+------------+------------+------------+------------+----------------|
```

**示例 2**  
PPL 查询：

```
os> source = t | fieldsummary includefields= id, status_code, request_path nulls=true
+------------------+-------------+------------+------------+------------+------------+------------+------------+----------------|
| Fields           | COUNT       | COUNT_DISTINCT    |  MIN  |  MAX   |  AVG   |  MEAN   |        STDDEV       | NUlls | TYPEOF |
|------------------+-------------+------------+------------+------------+------------+------------+------------+----------------|
|       "id"       |      6      |         6         | 1     |   6    |  3.5   |   3.5  |  1.8708286933869707  |  0    | "int"  |
+------------------+-------------+------------+------------+------------+------------+------------+------------+----------------|
| "status_code"    |      4      |         3         | 200   |   403  |  184.0 |  184.0  |  161.16699413961905 |  2    | "int"  |
+------------------+-------------+------------+------------+------------+------------+------------+------------+----------------|
| "request_path"   |      2      |         2         | /about| /home  |  0.0    |  0.0     |      0            |  2    |"string"|
+------------------+-------------+------------+------------+------------+------------+------------+------------+----------------|
```

#### expand 命令
<a name="supported-ppl-expand-command"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 功能，请参阅。[函数](#supported-ppl-functions)

使用 `expand` 命令，对 Array<Any> 或 Map<Any> 类型的字段进行展平处理，为每个元素或键值对生成单独的行。

**语法**  
使用以下语法：

```
expand <field> [As alias]
```

**字段**
+ 要扩展（展开）的字段。
+ 字段必须是受支持的类型。

**别名**
+ 可选。
+ 要使用的名称，而非原始字段名称。

**使用指南**  
expand 命令为指定数组或映射字段中的每个元素生成一行，其中：
+ 数组元素单独成行。
+ 映射键值对拆分为不同的行，每个键值都表示为一行。
+ 提供别名时，展开后的值将显示在别名下，而非原始字段名称下。

可将此命令与其他命令（例如 stats、eval 和 parse）结合使用，用于在扩展后对数据进行操作或提取。

**示例**
+ `source = table | expand employee | stats max(salary) as max by state, company `
+ `source = table | expand employee as worker | stats max(salary) as max by state, company `
+ `source = table | expand employee as worker | eval bonus = salary * 3 | fields worker, bonus` 
+ `source = table | expand employee | parse description '(?<email>.+@.+)' | fields employee, email` 
+ `source = table | eval array=json_array(1, 2, 3) | expand array as uid | fields name, occupation, uid `
+ `source = table | expand multi_valueA as multiA | expand multi_valueB as multiB` 

可将 expand 命令与其他命令（例如 eval、stats 等）结合使用。使用多个 expand 命令将创建每个复合数组或映射中所有内部元素的笛卡尔乘积。

**有效的 SQL 下推查询**  
expand 命令通过 LATERAL VIEW explode 转换为等效的 SQL 操作，从而能在 SQL 查询层级高效地展开数组或映射。

```
SELECT customer exploded_productId
FROM table
LATERAL VIEW explode(productId) AS exploded_productId
```

explode 命令提供以下功能：
+ 这是一种返回新列的列运算。
+ 会为已分解列中的每个元素创建一个新行。
+ 作为分解字段的一部分，内部空值将被忽略（没有一行代表 created/exploded 空值）。

#### PPL 函数
<a name="supported-ppl-functions-details"></a>

**Topics**
+ [

##### PPL 条件函数
](#supported-ppl-condition-functions)
+ [

##### PPL 加密哈希函数
](#supported-ppl-cryptographic-functions)
+ [

##### PPL 日期和时间函数
](#supported-ppl-date-time-functions)
+ [

##### PPL 表达式
](#supported-ppl-expressions)
+ [

##### PPL IP 地址函数
](#supported-ppl-ip-address-functions)
+ [

##### PPL JSON 函数
](#supported-ppl-json-functions)
+ [

##### PPL Lambda 函数
](#supported-ppl-lambda-functions)
+ [

##### PPL 数学函数
](#supported-ppl-math-functions)
+ [

##### PPL 字符串函数
](#supported-ppl-string-functions)
+ [

##### PPL 类型转换函数
](#supported-ppl-type-conversion-functions)

##### PPL 条件函数
<a name="supported-ppl-condition-functions"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 功能，请参阅。[函数](#supported-ppl-functions)

##### ISNULL
<a name="supported-ppl-condition-functions-isnull"></a>

**描述**：如果字段为 null，则 `isnull(field)` 返回 true。

**参数类型：**
+ 任何受支持的数据类型。

**返回类型：**
+ BOOLEAN

**示例**：

```
os> source=accounts | eval result = isnull(employer) | fields result, employer, firstname
fetched rows / total rows = 4/4
+----------+-------------+-------------+
| result   | employer    | firstname   |
|----------+-------------+-------------|
| False    | AnyCompany  | Mary        |
| False    | ExampleCorp | Jane        |
| False    | ExampleOrg  | Nikki       |
| True     | null        | Juan        |
+----------+-------------+-------------+
```

##### ISNOTNULL
<a name="supported-ppl-condition-functions-isnotnull"></a>

**描述**：如果字段不为 null，则 `isnotnull(field)` 返回 true。

**参数类型：**
+ 任何受支持的数据类型。

**返回类型：**
+ BOOLEAN

**示例**：

```
os> source=accounts | where not isnotnull(employer) | fields account_number, employer
fetched rows / total rows = 1/1
+------------------+------------+
| account_number   | employer   |
|------------------+------------|
| 18               | null       |
+------------------+------------+
```

##### EXISTS
<a name="supported-ppl-condition-functions-exists"></a>

**示例**：

```
os> source=accounts | where exists(email) | fields account_number, email
fetched rows / total rows = 1/1
```

##### IFNULL
<a name="supported-ppl-condition-functions-ifnull"></a>

**描述**：如果 `field1` 为 null，则 `ifnull(field1, field2)` 返回 `field2`。

**参数类型：**
+ 任何受支持的数据类型。
+ 如果两个参数的类型不同，则函数将无法通过语义检查。

**返回类型：**
+ 任何

**示例**：

```
os> source=accounts | eval result = ifnull(employer, 'default') | fields result, employer, firstname
fetched rows / total rows = 4/4
+------------+------------+-------------+
| result     | employer   | firstname   |
|------------+------------+-------------|
| AnyCompany | AnyCompany | Mary        |
| ExampleCorp| ExampleCorp| Jane        |
| ExampleOrg | ExampleOrg | Nikki       |
| default    | null       | Juan        |
+------------+------------+-------------+
```

##### NULLIF
<a name="supported-ppl-condition-functions-nullif"></a>

**描述**：如果两个参数相同，则 `nullif(field1, field2)` 返回 null，否则返回 field1。

**参数类型：**
+ 任何受支持的数据类型。
+ 如果两个参数的类型不同，则函数将无法通过语义检查。

**返回类型：**
+ 任何

**示例**：

```
os> source=accounts | eval result = nullif(employer, 'AnyCompany') | fields result, employer, firstname
fetched rows / total rows = 4/4
+----------------+----------------+-------------+
| result         | employer       | firstname   |
|----------------+----------------+-------------|
| null           | AnyCompany     | Mary        |
| ExampleCorp    | ExampleCorp    | Jane        |
| ExampleOrg     | ExampleOrg     | Nikki       |
| null           | null           | Juan        |
+----------------+----------------+-------------+
```

##### IF
<a name="supported-ppl-condition-functions-if"></a>

**描述**：如果条件为 true，则 `if(condition, expr1, expr2)` 返回 `expr1`，否则返回 `expr2`。

**参数类型：**
+ 任何受支持的数据类型。
+ 如果两个参数的类型不同，则函数将无法通过语义检查。

**返回类型：**
+ 任何

**示例**：

```
os> source=accounts | eval result = if(true, firstname, lastname) | fields result, firstname, lastname
fetched rows / total rows = 4/4
+----------+-------------+----------+
| result   | firstname | lastname   |
|----------+-------------+----------|
| Jane     | Jane      | Doe        |
| Mary     | Mary      | Major      |
| Pat      | Pat       | Candella   |
| Dale     | Jorge     | Souza      |
+----------+-----------+------------+

os> source=accounts | eval result = if(false, firstname, lastname) | fields result, firstname, lastname
fetched rows / total rows = 4/4
+----------+-------------+------------+
| result   | firstname   | lastname   |
|----------+-------------+------------|
| Doe      | Jane        | Doe        |
| Major    | Mary        | Major      |
| Candella | Pat         | Candella   |
| Souza    | Jorge       | Souza      |
+----------+-------------+------------+

os> source=accounts | eval is_vip = if(age > 30 AND isnotnull(employer), true, false) | fields is_vip, firstname, lastname
fetched rows / total rows = 4/4
+----------+-------------+------------+
| is_vip   | firstname   | lastname   |
|----------+-------------+------------|
| True     | Jane        | Doe        |
| True     | Mary        | Major      |
| False    | Pat         | Candella   |
| False    | Jorge       | Souza      |
+----------+-------------+------------+
```

##### PPL 加密哈希函数
<a name="supported-ppl-cryptographic-functions"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 功能，请参阅。[函数](#supported-ppl-functions)

##### MD5
<a name="supported-ppl-cryptographic-functions-md5"></a>

MD5 计算 MD5 摘要并以 32 个字符的十六进制字符串形式返回该值。

**用法**：`md5('hello')`

**参数类型：**
+ string

**返回类型：**
+ string

**示例**：

```
os> source=people | eval `MD5('hello')` = MD5('hello') | fields `MD5('hello')`
fetched rows / total rows = 1/1
+----------------------------------+
| MD5('hello')                     |
|----------------------------------|
| <32 character hex string>        |
+----------------------------------+
```

##### SHA1
<a name="supported-ppl-cryptographic-functions-sha1"></a>

SHA1 返回 SHA-1 的十六进制字符串结果。

**用法**：`sha1('hello')`

**参数类型：**
+ string

**返回类型：**
+ string

**示例**：

```
os> source=people | eval `SHA1('hello')` = SHA1('hello') | fields `SHA1('hello')`
fetched rows / total rows = 1/1
+------------------------------------------+
| SHA1('hello')                            |
|------------------------------------------|
| <40-character SHA-1 hash result>         |
+------------------------------------------+
```

##### SHA2
<a name="supported-ppl-cryptographic-functions-sha2"></a>

SHA2 返回 SHA-2 系列哈希函数（SHA-224、SHA-256、SHA-384 和 SHA-512）的十六进制字符串结果。numBits 表示结果所需的位长度，其值必须为 224、256、384、512

**用法：**
+ `sha2('hello',256)`
+ `sha2('hello',512)`

**参数类型：**
+ STRING、INTEGER

**返回类型：**
+ string

**示例**：

```
os> source=people | eval `SHA2('hello',256)` = SHA2('hello',256) | fields `SHA2('hello',256)`
fetched rows / total rows = 1/1
+------------------------------------------------------------------+
| SHA2('hello',256)                                                |
|------------------------------------------------------------------|
| <64-character SHA-256 hash result>                               |
+------------------------------------------------------------------+

os> source=people | eval `SHA2('hello',512)` = SHA2('hello',512) | fields `SHA2('hello',512)`
fetched rows / total rows = 1/1
+------------------------------------------------------------------+
| SHA2('hello',512)                                                |                                                                |
|------------------------------------------------------------------|
| <128-character SHA-512 hash result>                              |
+------------------------------------------------------------------+
```

##### PPL 日期和时间函数
<a name="supported-ppl-date-time-functions"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 功能，请参阅。[函数](#supported-ppl-functions)

##### `DAY`
<a name="supported-ppl-date-time-functions-day"></a>

**用法**：`DAY(date)` 提取日期的月份天数，范围为 1 至 31。

**参数类型**：STRING/DATE/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`DAYOFMONTH`、`DAY_OF_MONTH`

**示例**：

```
os> source=people | eval `DAY(DATE('2020-08-26'))` = DAY(DATE('2020-08-26')) | fields `DAY(DATE('2020-08-26'))`
fetched rows / total rows = 1/1
+---------------------------+
| DAY(DATE('2020-08-26'))   |
|---------------------------|
| 26                        |
+---------------------------+
```

##### `DAYOFMONTH`
<a name="supported-ppl-date-time-functions-dayofmonth"></a>

**用法**：`DAYOFMONTH(date)` 提取日期的月份天数，范围为 1 至 31。

**参数类型**：STRING/DATE/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`DAY`、`DAY_OF_MONTH`

**示例**：

```
os> source=people | eval `DAYOFMONTH(DATE('2020-08-26'))` = DAYOFMONTH(DATE('2020-08-26')) | fields `DAYOFMONTH(DATE('2020-08-26'))`
fetched rows / total rows = 1/1
+----------------------------------+
| DAYOFMONTH(DATE('2020-08-26'))   |
|----------------------------------|
| 26                               |
+----------------------------------+
```

##### `DAY_OF_MONTH`
<a name="supported-ppl-date-time-functions-day-of-month"></a>

**用法**：`DAY_OF_MONTH(DATE)` 提取日期的月份天数，范围为 1 至 31。

**参数类型**：STRING/DATE/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`DAY`、`DAYOFMONTH`

**示例**：

```
os> source=people | eval `DAY_OF_MONTH(DATE('2020-08-26'))` = DAY_OF_MONTH(DATE('2020-08-26')) | fields `DAY_OF_MONTH(DATE('2020-08-26'))`
fetched rows / total rows = 1/1
+------------------------------------+
| DAY_OF_MONTH(DATE('2020-08-26'))   |
|------------------------------------|
| 26                                 |
+------------------------------------+
```

##### `DAYOFWEEK`
<a name="supported-ppl-date-time-functions-dayofweek"></a>

**用法**：`DAYOFWEEK(DATE)` 返回日期的工作日索引（1 = 星期日，2 = 星期一，...，7 = 星期六）。

**参数类型**：STRING/DATE/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`DAY_OF_WEEK`

**示例**：

```
os> source=people | eval `DAYOFWEEK(DATE('2020-08-26'))` = DAYOFWEEK(DATE('2020-08-26')) | fields `DAYOFWEEK(DATE('2020-08-26'))`
fetched rows / total rows = 1/1
+---------------------------------+
| DAYOFWEEK(DATE('2020-08-26'))   |
|---------------------------------|
| 4                               |
+---------------------------------+
```

##### `DAY_OF_WEEK`
<a name="supported-ppl-date-time-functions-day-of-week"></a>

**用法**：`DAY_OF_WEEK(DATE)` 返回日期的工作日索引（1 = 星期日，2 = 星期一，...，7 = 星期六）。

**参数类型**：STRING/DATE/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`DAYOFWEEK`

**示例**：

```
os> source=people | eval `DAY_OF_WEEK(DATE('2020-08-26'))` = DAY_OF_WEEK(DATE('2020-08-26')) | fields `DAY_OF_WEEK(DATE('2020-08-26'))`
fetched rows / total rows = 1/1
+-----------------------------------+
| DAY_OF_WEEK(DATE('2020-08-26'))   |
|-----------------------------------|
| 4                                 |
+-----------------------------------+
```

##### `DAYOFYEAR`
<a name="supported-ppl-date-time-functions-dayofyear"></a>

**用法**：`DAYOFYEAR(DATE)` 返回日期的年份天数，范围为 1 至 366。

**参数类型**：STRING/DATE/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`DAY_OF_YEAR`

**示例**：

```
os> source=people | eval `DAYOFYEAR(DATE('2020-08-26'))` = DAYOFYEAR(DATE('2020-08-26')) | fields `DAYOFYEAR(DATE('2020-08-26'))`
fetched rows / total rows = 1/1
+---------------------------------+
| DAYOFYEAR(DATE('2020-08-26'))   |
|---------------------------------|
| 239                             |
+---------------------------------+
```

##### `DAY_OF_YEAR`
<a name="supported-ppl-date-time-functions-day-of-year"></a>

**用法**：`DAY_OF_YEAR(DATE)` 返回日期的年份天数，范围为 1 至 366。

**参数类型**：STRING/DATE/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`DAYOFYEAR`

**示例**：

```
os> source=people | eval `DAY_OF_YEAR(DATE('2020-08-26'))` = DAY_OF_YEAR(DATE('2020-08-26')) | fields `DAY_OF_YEAR(DATE('2020-08-26'))`
fetched rows / total rows = 1/1
+-----------------------------------+
| DAY_OF_YEAR(DATE('2020-08-26'))   |
|-----------------------------------|
| 239                               |
+-----------------------------------+
```

##### `DAYNAME`
<a name="supported-ppl-date-time-functions-dayname"></a>

**用法**：`DAYNAME(DATE)` 返回日期的星期名称，包括星期一、星期二、星期三、星期五、星期六和星期日。

**参数类型**：STRING/DATE/TIMESTAMP

**返回类型**：STRING

**示例**：

```
os> source=people | eval `DAYNAME(DATE('2020-08-26'))` = DAYNAME(DATE('2020-08-26')) | fields `DAYNAME(DATE('2020-08-26'))`
fetched rows / total rows = 1/1
+-------------------------------+
| DAYNAME(DATE('2020-08-26'))   |
|-------------------------------|
| Wednesday                     |
+-------------------------------+
```

##### `FROM_UNIXTIME`
<a name="supported-ppl-date-time-functions-from-unixtime"></a>

**用法**：`FROM_UNIXTIME` 返回参数的表示形式，该参数以时间戳或字符串值的形式给出。此函数对 `UNIX_TIMESTAMP` 函数执行反向转换。

如果提供第二个参数，则 `FROM_UNIXTIME` 将使用该参数对结果进行格式化，使其类似于 `DATE_FORMAT` 函数的输出效果。

如果时间戳超出 1970-01-01 00:00:00 至 3001-01-18 23:59:59.999999（0 至 32536771199.999999 epoch 时间）的范围，则该函数返回 `NULL`。

**参数类型**：DOUBLE、STRING

**返回类型映射**：

DOUBLE -> TIMESTAMP

DOUBLE, STRING -> STRING

**示例：**

```
os> source=people | eval `FROM_UNIXTIME(1220249547)` = FROM_UNIXTIME(1220249547) | fields `FROM_UNIXTIME(1220249547)`
fetched rows / total rows = 1/1
+-----------------------------+
| FROM_UNIXTIME(1220249547)   |
|-----------------------------|
| 2008-09-01 06:12:27         |
+-----------------------------+

os> source=people | eval `FROM_UNIXTIME(1220249547, 'HH:mm:ss')` = FROM_UNIXTIME(1220249547, 'HH:mm:ss') | fields `FROM_UNIXTIME(1220249547, 'HH:mm:ss')`
fetched rows / total rows = 1/1
+-----------------------------------------+
| FROM_UNIXTIME(1220249547, 'HH:mm:ss')   |
|-----------------------------------------|
| 06:12:27                                |
+-----------------------------------------+
```

##### `HOUR`
<a name="supported-ppl-date-time-functions-hour"></a>

**用法**：`HOUR(TIME)` 提取时间的小时值。

与标准时间不同，此函数中的时间值范围可大于 23。因此，`HOUR(TIME)` 的返回值可大于 23。

**参数类型**：STRING/TIME/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`HOUR_OF_DAY`

**示例**：

```
os> source=people | eval `HOUR(TIME('01:02:03'))` = HOUR(TIME('01:02:03')) | fields `HOUR(TIME('01:02:03'))`
fetched rows / total rows = 1/1
+--------------------------+
| HOUR(TIME('01:02:03'))   |
|--------------------------|
| 1                        |
+--------------------------+
```

##### `HOUR_OF_DAY`
<a name="supported-ppl-date-time-functions-hour-of-day"></a>

**用法**：`HOUR_OF_DAY(TIME)` 提取给定时间的小时值。

与标准时间不同，此函数中的时间值范围可大于 23。因此，`HOUR_OF_DAY(TIME)` 的返回值可大于 23。

**参数类型**：STRING/TIME/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`HOUR`

**示例**：

```
os> source=people | eval `HOUR_OF_DAY(TIME('01:02:03'))` = HOUR_OF_DAY(TIME('01:02:03')) | fields `HOUR_OF_DAY(TIME('01:02:03'))`
fetched rows / total rows = 1/1
+---------------------------------+
| HOUR_OF_DAY(TIME('01:02:03'))   |
|---------------------------------|
| 1                               |
+---------------------------------+
```

##### `LAST_DAY`
<a name="supported-ppl-date-time-functions-last-day"></a>

**用法**：`LAST_DAY` 返回指定日期参数对应月份的最后一天，作为 DATE 值。

**参数类型**：DATE/STRING/TIMESTAMP/TIME

**返回类型**：DATE

**示例**：

```
os> source=people | eval `last_day('2023-02-06')` = last_day('2023-02-06') | fields `last_day('2023-02-06')`
fetched rows / total rows = 1/1
+--------------------------+
| last_day('2023-02-06')   |
|--------------------------|
| 2023-02-28               |
+--------------------------+
```

##### `LOCALTIMESTAMP`
<a name="supported-ppl-date-time-functions-localtimestamp"></a>

**用法**：`LOCALTIMESTAMP()` 是 `NOW()` 的同义词。

**示例**：

```
> source=people | eval `LOCALTIMESTAMP()` = LOCALTIMESTAMP() | fields `LOCALTIMESTAMP()`
fetched rows / total rows = 1/1
+---------------------+
| LOCALTIMESTAMP()    |
|---------------------|
| 2022-08-02 15:54:19 |
+---------------------+
```

##### `LOCALTIME`
<a name="supported-ppl-date-time-functions-localtime"></a>

**用法**：`LOCALTIME()` 是 `NOW()` 的同义词。

**示例**：

```
> source=people | eval `LOCALTIME()` = LOCALTIME() | fields `LOCALTIME()`
fetched rows / total rows = 1/1
+---------------------+
| LOCALTIME()         |
|---------------------|
| 2022-08-02 15:54:19 |
+---------------------+
```

##### `MAKE_DATE`
<a name="supported-ppl-date-time-functions-make-date"></a>

**用法**：`MAKE_DATE` 根据给定的年、月、日值返回日期值。所有参数均四舍五入为整数。

**规格**：1。MAKE\$1DATE(INTEGER, INTEGER, INTEGER) -> DATE

**参数类型**：INTEGER、INTEGER、INTEGER

**返回类型**：DATE

**示例**：

```
os> source=people | eval `MAKE_DATE(1945, 5, 9)` = MAKEDATE(1945, 5, 9) | fields `MAKEDATE(1945, 5, 9)`
fetched rows / total rows = 1/1
+------------------------+
| MAKEDATE(1945, 5, 9)   |
|------------------------|
| 1945-05-09             |
+------------------------+
```

##### `MINUTE`
<a name="supported-ppl-date-time-functions-minute"></a>

**用法**：`MINUTE(TIME)` 返回给定时间的分钟部分，以 0 到 59 范围内的整数形式表示。

**参数类型**：STRING/TIME/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`MINUTE_OF_HOUR`

**示例**：

```
os> source=people | eval `MINUTE(TIME('01:02:03'))` =  MINUTE(TIME('01:02:03')) | fields `MINUTE(TIME('01:02:03'))`
fetched rows / total rows = 1/1
+----------------------------+
| MINUTE(TIME('01:02:03'))   |
|----------------------------|
| 2                          |
+----------------------------+
```

##### `MINUTE_OF_HOUR`
<a name="supported-ppl-date-time-functions-minute-of-hour"></a>

**用法**：`MINUTE_OF_HOUR(TIME)` 返回给定时间的分钟部分，以 0 到 59 范围内的整数形式表示。

**参数类型**：STRING/TIME/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`MINUTE`

**示例**：

```
os> source=people | eval `MINUTE_OF_HOUR(TIME('01:02:03'))` =  MINUTE_OF_HOUR(TIME('01:02:03')) | fields `MINUTE_OF_HOUR(TIME('01:02:03'))`
fetched rows / total rows = 1/1
+------------------------------------+
| MINUTE_OF_HOUR(TIME('01:02:03'))   |
|------------------------------------|
| 2                                  |
+------------------------------------+
```

##### `MONTH`
<a name="supported-ppl-date-time-functions-month"></a>

**用法**：`MONTH(DATE)` 返回给定日期的月份，以整数形式表示，范围为 1 到 12（其中 1 代表一月，12 代表十二月）。

**参数类型**：STRING/DATE/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`MONTH_OF_YEAR`

**示例**：

```
os> source=people | eval `MONTH(DATE('2020-08-26'))` =  MONTH(DATE('2020-08-26')) | fields `MONTH(DATE('2020-08-26'))`
fetched rows / total rows = 1/1
+-----------------------------+
| MONTH(DATE('2020-08-26'))   |
|-----------------------------|
| 8                           |
+-----------------------------+
```

##### `MONTHNAME`
<a name="supported-ppl-date-time-functions-monthname"></a>

**用法**：`MONTHNAME(DATE)` 返回给定日期的月份，以整数形式表示，范围为 1 到 12（其中 1 代表一月，12 代表十二月）。

**参数类型**：STRING/DATE/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`MONTH_OF_YEAR`

**示例**：

```
os> source=people | eval `MONTHNAME(DATE('2020-08-26'))` = MONTHNAME(DATE('2020-08-26')) | fields `MONTHNAME(DATE('2020-08-26'))`
fetched rows / total rows = 1/1
+---------------------------------+
| MONTHNAME(DATE('2020-08-26'))   |
|---------------------------------|
| August                          |
+---------------------------------+
```

##### `MONTH_OF_YEAR`
<a name="supported-ppl-date-time-functions-month-of-year"></a>

**用法**：`MONTH_OF_YEAR(DATE)` 返回给定日期的月份，以整数形式表示，范围为 1 到 12（其中 1 代表一月，12 代表十二月）。

**参数类型**：STRING/DATE/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`MONTH`

**示例**：

```
os> source=people | eval `MONTH_OF_YEAR(DATE('2020-08-26'))` =  MONTH_OF_YEAR(DATE('2020-08-26')) | fields `MONTH_OF_YEAR(DATE('2020-08-26'))`
fetched rows / total rows = 1/1
+-------------------------------------+
| MONTH_OF_YEAR(DATE('2020-08-26'))   |
|-------------------------------------|
| 8                                   |
+-------------------------------------+
```

##### `NOW`
<a name="supported-ppl-date-time-functions-now"></a>

**用法**：`NOW`以 'YYYY-MM-DD hh: mm: s `TIMESTAMP` s' 格式返回当前日期和时间。该值采用集群时区表示。

**注意**  
`NOW()` 返回表示语句何时开始执行的常量时间。这与 `SYSDATE()` 不同，后者返回精确的执行时间。

**返回类型**：TIMESTAMP

**规范**：NOW() -> TIMESTAMP

**示例**：

```
os> source=people | eval `value_1` = NOW(), `value_2` = NOW() | fields `value_1`, `value_2`
fetched rows / total rows = 1/1
+---------------------+---------------------+
| value_1             | value_2             |
|---------------------+---------------------|
| 2022-08-02 15:39:05 | 2022-08-02 15:39:05 |
+---------------------+---------------------+
```

##### `QUARTER`
<a name="supported-ppl-date-time-functions-quarter"></a>

**用法**：`QUARTER(DATE)` 返回给定日期的季度，以整数形式表示，范围为 1 到 4。

**参数类型**：STRING/DATE/TIMESTAMP

**返回类型：**INTEGER

**示例**：

```
os> source=people | eval `QUARTER(DATE('2020-08-26'))` = QUARTER(DATE('2020-08-26')) | fields `QUARTER(DATE('2020-08-26'))`
fetched rows / total rows = 1/1
+-------------------------------+
| QUARTER(DATE('2020-08-26'))   |
|-------------------------------|
| 3                             |
+-------------------------------+
```

##### `SECOND`
<a name="supported-ppl-date-time-functions-second"></a>

**用法**：`SECOND(TIME)` 返回给定时间的秒钟，以整数形式表示，范围为 0 到 59。

**参数类型**：STRING/TIME/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`SECOND_OF_MINUTE`

**示例**：

```
os> source=people | eval `SECOND(TIME('01:02:03'))` = SECOND(TIME('01:02:03')) | fields `SECOND(TIME('01:02:03'))`
fetched rows / total rows = 1/1
+----------------------------+
| SECOND(TIME('01:02:03'))   |
|----------------------------|
| 3                          |
+----------------------------+
```

##### `SECOND_OF_MINUTE`
<a name="supported-ppl-date-time-functions-second-of-minute"></a>

**用法**：`SECOND_OF_MINUTE(TIME)` 返回给定时间的秒钟，以整数形式表示，范围为 0 到 59。

**参数类型**：STRING/TIME/TIMESTAMP

**返回类型**：INTEGER

**同义词**：`SECOND`

**示例**：

```
os> source=people | eval `SECOND_OF_MINUTE(TIME('01:02:03'))` = SECOND_OF_MINUTE(TIME('01:02:03')) | fields `SECOND_OF_MINUTE(TIME('01:02:03'))`
fetched rows / total rows = 1/1
+--------------------------------------+
| SECOND_OF_MINUTE(TIME('01:02:03'))   |
|--------------------------------------|
| 3                                    |
+--------------------------------------+
```

##### `SUBDATE`
<a name="supported-ppl-date-time-functions-subdate"></a>

**用法**：`SUBDATE(DATE, DAYS)` 从给定日期中减去第二个参数（例如 `DATE` 或 `DAYS`）。

**参数类型**：DATE/TIMESTAMP、LONG

**返回类型映射**：(DATE, LONG) -> DATE

**反义词**：`ADDDATE`

**示例**：

```
os> source=people | eval `'2008-01-02' - 31d` = SUBDATE(DATE('2008-01-02'), 31), `'2020-08-26' - 1` = SUBDATE(DATE('2020-08-26'), 1), `ts '2020-08-26 01:01:01' - 1` = SUBDATE(TIMESTAMP('2020-08-26 01:01:01'), 1) | fields `'2008-01-02' - 31d`, `'2020-08-26' - 1`, `ts '2020-08-26 01:01:01' - 1`
fetched rows / total rows = 1/1
+----------------------+--------------------+--------------------------------+
| '2008-01-02' - 31d   | '2020-08-26' - 1   | ts '2020-08-26 01:01:01' - 1   |
|----------------------+--------------------+--------------------------------|
| 2007-12-02 00:00:00  | 2020-08-25         | 2020-08-25 01:01:01            |
+----------------------+--------------------+--------------------------------+
```

##### `SYSDATE`
<a name="supported-ppl-date-time-functions-sysdate"></a>

**用法**：以 'YYYY-MM-DD hh: mm: ss.nnnnnn' 格式的`TIMESTAMP`值`SYSDATE()`返回当前日期和时间。

`SYSDATE()` 返回其执行的精确时间。这与 NOW() 不同，后者返回常量时间，指示语句开始执行的时间。

**可选参数类型**：INTEGER（0 到 6）：指定返回值中秒数小数部分的位数。

**返回类型**：TIMESTAMP

**示例**：

```
os> source=people | eval `SYSDATE()` = SYSDATE() | fields `SYSDATE()`
fetched rows / total rows = 1/1
+----------------------------+
| SYSDATE()                  |
|----------------------------|
| 2022-08-02 15:39:05.123456 |
+----------------------------+
```

##### `TIMESTAMP`
<a name="supported-ppl-date-time-functions-timestamp"></a>

**用法**：`TIMESTAMP(EXPR)` 构造以输入字符串 `expr` 作为时间戳的时间戳类型。

使用单个参数，`TIMESTAMP(expr)` 根据输入构造时间戳。如果 `expr` 是字符串，则将其解释为时间戳。对于非字符串参数，该函数使用 UTC 时区将 `expr` 转换为时间戳。如果 `expr` 是 `TIME` 值，该函数在转换前应用今日日期。

与两个参数结合使用时，`TIMESTAMP(expr1, expr2)` 将时间表达式（`expr2`）添加到日期或时间戳表达式（`expr1`）中，并将结果作为时间戳值返回。

**参数类型**：STRING/DATE/TIME/TIMESTAMP

**返回类型映射：**

(STRING/DATE/TIME/TIMESTAMP)-> 时间戳

(STRING/DATE/TIME/TIMESTAMP, STRING/DATE/TIME/TIMESTAMP)-> 时间戳

**示例**：

```
os> source=people | eval `TIMESTAMP('2020-08-26 13:49:00')` = TIMESTAMP('2020-08-26 13:49:00'), `TIMESTAMP('2020-08-26 13:49:00', TIME('12:15:42'))` = TIMESTAMP('2020-08-26 13:49:00', TIME('12:15:42')) | fields `TIMESTAMP('2020-08-26 13:49:00')`, `TIMESTAMP('2020-08-26 13:49:00', TIME('12:15:42'))`
fetched rows / total rows = 1/1
+------------------------------------+------------------------------------------------------+
| TIMESTAMP('2020-08-26 13:49:00')   | TIMESTAMP('2020-08-26 13:49:00', TIME('12:15:42'))   |
|------------------------------------+------------------------------------------------------|
| 2020-08-26 13:49:00                | 2020-08-27 02:04:42                                  |
+------------------------------------+------------------------------------------------------+
```

##### `UNIX_TIMESTAMP`
<a name="supported-ppl-date-time-functions-unix-timestamp"></a>

**用法**：`UNIX_TIMESTAMP` 将给定的日期参数转换为 Unix 时间（自 epoch（始于 1970 年初）以来的秒数）。如果未提供参数，则返回当前的 Unix 时间。

日期参数可以是 `DATE`、`TIMESTAMP` 字符串或以下格式之一的数字：`YYMMDD`、`YYMMDDhhmmss`、`YYYYMMDD` 或 `YYYYMMDDhhmmss`。如果参数包含时间分量，则可以选择包含秒的分数部分。

如果参数的格式无效或超出 1970-01-01 00:00:00 至 3001-01-18 23:59:59.999999（0 至 32536771199.999999 epoch 时间）的范围，则该函数返回 `NULL`。

该函数接受 `DATE`、`TIMESTAMP`、或 `DOUBLE` 作为参数类型，或不接受任何参数。该函数始终返回代表 Unix 时间戳的 `DOUBLE` 值。

要进行反向转换，可使用 FROM\$1UNIXTIME 函数。

**参数类型**：<NONE>/DOUBLE/DATE/TIMESTAMP

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `UNIX_TIMESTAMP(double)` = UNIX_TIMESTAMP(20771122143845), `UNIX_TIMESTAMP(timestamp)` = UNIX_TIMESTAMP(TIMESTAMP('1996-11-15 17:05:42')) | fields `UNIX_TIMESTAMP(double)`, `UNIX_TIMESTAMP(timestamp)`
fetched rows / total rows = 1/1
+--------------------------+-----------------------------+
| UNIX_TIMESTAMP(double)   | UNIX_TIMESTAMP(timestamp)   |
|--------------------------+-----------------------------|
| 3404817525.0             | 848077542.0                 |
+--------------------------+-----------------------------+
```

##### `WEEK`
<a name="supported-ppl-date-time-functions-week"></a>

**用法**：`WEEK(DATE)` 返回给定日期的星期序号。

**参数类型**：DATE/TIMESTAMP/STRING

**返回类型**：INTEGER

**同义词**：`WEEK_OF_YEAR`

**示例**：

```
os> source=people | eval `WEEK(DATE('2008-02-20'))` = WEEK(DATE('2008-02-20')) | fields `WEEK(DATE('2008-02-20'))`
fetched rows / total rows = 1/1
+----------------------------+
| WEEK(DATE('2008-02-20'))   |
|----------------------------|
| 8                          |
+----------------------------+
```

##### `WEEKDAY`
<a name="supported-ppl-date-time-functions-weekday"></a>

**用法**：`WEEKDAY(DATE)` 返回日期的工作日索引（0 = 星期一，1 = 星期二，...，6 = 星期日）。

这与 `dayofweek` 函数类似，但每天返回不同的索引。

**参数类型**：STRING/DATE/TIME/TIMESTAMP

**返回类型：**INTEGER

**示例**：

```
os> source=people | eval `weekday(DATE('2020-08-26'))` = weekday(DATE('2020-08-26')) | eval `weekday(DATE('2020-08-27'))` = weekday(DATE('2020-08-27')) | fields `weekday(DATE('2020-08-26'))`, `weekday(DATE('2020-08-27'))`
fetched rows / total rows = 1/1
+-------------------------------+-------------------------------+
| weekday(DATE('2020-08-26'))   | weekday(DATE('2020-08-27'))   |
|-------------------------------+-------------------------------|
| 2                             | 3                             |
+-------------------------------+-------------------------------+
```

##### `WEEK_OF_YEAR`
<a name="supported-ppl-date-time-functions-week-of-year"></a>

**用法**：`WEEK_OF_YEAR(DATE)` 返回给定日期的星期序号。

**参数类型**：DATE/TIMESTAMP/STRING

**返回类型**：INTEGER

**同义词**：`WEEK`

**示例**：

```
os> source=people | eval `WEEK_OF_YEAR(DATE('2008-02-20'))` = WEEK(DATE('2008-02-20'))| fields `WEEK_OF_YEAR(DATE('2008-02-20'))`
fetched rows / total rows = 1/1
+------------------------------------+
| WEEK_OF_YEAR(DATE('2008-02-20'))   |
|------------------------------------|
| 8                                  |
+------------------------------------+
```

##### `YEAR`
<a name="supported-ppl-date-time-functions-year"></a>

**用法**：`YEAR(DATE)` 返回日期的年份，范围为 1000 到 9999，或者返回 0 表示“零”日期。

**参数类型**：STRING/DATE/TIMESTAMP

**返回类型：**INTEGER

**示例**：

```
os> source=people | eval `YEAR(DATE('2020-08-26'))` = YEAR(DATE('2020-08-26')) | fields `YEAR(DATE('2020-08-26'))`
fetched rows / total rows = 1/1
+----------------------------+
| YEAR(DATE('2020-08-26'))   |
|----------------------------|
| 2020                       |
+----------------------------+
```

##### `DATE_ADD`
<a name="supported-ppl-date-time-functions-date-add"></a>

**用法**：`DATE_ADD(date, INTERVAL expr unit)` 将指定的时间间隔添加到给定日期。

**参数类型**：DATE、INTERVAL

**返回类型**：DATE

**反义词**：`DATE_SUB`

**示例**：

```
os> source=people | eval `'2020-08-26' + 1d` = DATE_ADD(DATE('2020-08-26'), INTERVAL 1 DAY) | fields `'2020-08-26' + 1d`
fetched rows / total rows = 1/1
+---------------------+
| '2020-08-26' + 1d   |
|---------------------|
| 2020-08-27          |
+---------------------+
```

##### `DATE_SUB`
<a name="supported-ppl-date-time-functions-date-sub"></a>

**用法**：`DATE_SUB(date, INTERVAL expr unit)` 从日期中减去间隔 expr。

**参数类型**：DATE、INTERVAL

**返回类型**：DATE

**反义词**：`DATE_ADD`

**示例**：

```
os> source=people | eval `'2008-01-02' - 31d` = DATE_SUB(DATE('2008-01-02'), INTERVAL 31 DAY) | fields `'2008-01-02' - 31d`
fetched rows / total rows = 1/1
+---------------------+
| '2008-01-02' - 31d  |
|---------------------|
| 2007-12-02          |
+---------------------+
```

##### `TIMESTAMPADD`
<a name="supported-ppl-date-time-functions-timestampadd"></a>

**用法**：为给定日期添加指定时间间隔后，返回 `TIMESTAMP` 值。

**论点**：
+ 间隔：INTERVAL（SECOND、MINUTE、HOUR、DAY、WEEK、MONTH、QUARTER、YEAR） 
+ 整数：INTEGER 
+ 日期：DATE、TIMESTAMP 或 STRING

如果您提供 `STRING` 作为日期参数，请将其格式化为有效的 `TIMESTAMP`。该函数会自动将 `DATE` 参数转换为 `TIMESTAMP`。

**示例：**

```
os> source=people | eval `TIMESTAMPADD(DAY, 17, '2000-01-01 00:00:00')` = TIMESTAMPADD(DAY, 17, '2000-01-01 00:00:00') | eval `TIMESTAMPADD(QUARTER, -1, '2000-01-01 00:00:00')` = TIMESTAMPADD(QUARTER, -1, '2000-01-01 00:00:00') | fields `TIMESTAMPADD(DAY, 17, '2000-01-01 00:00:00')`, `TIMESTAMPADD(QUARTER, -1, '2000-01-01 00:00:00')`
fetched rows / total rows = 1/1
+----------------------------------------------+--------------------------------------------------+
| TIMESTAMPADD(DAY, 17, '2000-01-01 00:00:00') | TIMESTAMPADD(QUARTER, -1, '2000-01-01 00:00:00') |
|----------------------------------------------+--------------------------------------------------|
| 2000-01-18 00:00:00                          | 1999-10-01 00:00:00                              |
+----------------------------------------------+--------------------------------------------------+
```

##### `TIMESTAMPDIFF`
<a name="supported-ppl-date-time-functions-timestampdiff"></a>

**用法**：以指定的间隔单位`TIMESTAMPDIFF(interval, start, end)`返回开始和结束 date/times 之间的差。

**论点**：
+ 间隔：INTERVAL（SECOND、MINUTE、HOUR、DAY、WEEK、MONTH、QUARTER、YEAR） 
+ 开始：DATE、TIMESTAMP 或 STRING 
+ 结束：DATE、TIMESTAMP 或 STRING

该函数会在适当情况下自动将参数转换为 `TIMESTAMP`。将 `STRING` 参数格式化为有效的 `TIMESTAMP`。

**示例：**

```
os> source=people | eval `TIMESTAMPDIFF(YEAR, '1997-01-01 00:00:00', '2001-03-06 00:00:00')` = TIMESTAMPDIFF(YEAR, '1997-01-01 00:00:00', '2001-03-06 00:00:00') | eval `TIMESTAMPDIFF(SECOND, timestamp('1997-01-01 00:00:23'), timestamp('1997-01-01 00:00:00'))` = TIMESTAMPDIFF(SECOND, timestamp('1997-01-01 00:00:23'), timestamp('1997-01-01 00:00:00')) | fields `TIMESTAMPDIFF(YEAR, '1997-01-01 00:00:00', '2001-03-06 00:00:00')`, `TIMESTAMPDIFF(SECOND, timestamp('1997-01-01 00:00:23'), timestamp('1997-01-01 00:00:00'))`
fetched rows / total rows = 1/1
+-------------------------------------------------------------------+-------------------------------------------------------------------------------------------+
| TIMESTAMPDIFF(YEAR, '1997-01-01 00:00:00', '2001-03-06 00:00:00') | TIMESTAMPDIFF(SECOND, timestamp('1997-01-01 00:00:23'), timestamp('1997-01-01 00:00:00')) |
|-------------------------------------------------------------------+-------------------------------------------------------------------------------------------|
| 4                                                                 | -23                                                                                       |
+-------------------------------------------------------------------+-------------------------------------------------------------------------------------------+
```

##### `UTC_TIMESTAMP`
<a name="supported-ppl-date-time-functions-utc-timestamp"></a>

**用法**：`UTC_TIMESTAMP` 返回当前的 UTC 时间戳，以值表示，格式为“YYYY-MM-DD hh:mm:ss”。

**返回类型**：TIMESTAMP

**规范**：UTC\$1TIMESTAMP() -> TIMESTAMP

**示例**：

```
> source=people | eval `UTC_TIMESTAMP()` = UTC_TIMESTAMP() | fields `UTC_TIMESTAMP()`
fetched rows / total rows = 1/1
+---------------------+
| UTC_TIMESTAMP()     |
|---------------------|
| 2022-10-03 17:54:28 |
+---------------------+
```

##### `CURRENT_TIMEZONE`
<a name="supported-ppl-date-time-functions-current-timezone"></a>

**用法**：`CURRENT_TIMEZONE` 返回当前的本地时区。

**返回类型**：STRING

**示例**：

```
> source=people | eval `CURRENT_TIMEZONE()` = CURRENT_TIMEZONE() | fields `CURRENT_TIMEZONE()`
fetched rows / total rows = 1/1
+------------------------+
| CURRENT_TIMEZONE()     |
|------------------------|
| America/Chicago        |
+------------------------+
```

##### PPL 表达式
<a name="supported-ppl-expressions"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 功能，请参阅。[函数](#supported-ppl-functions)

表达式，尤其是值表达式，返回标量值。表达式具有不同的类型和形式。例如，存在作为原子表达式的字面值，以及基于这些字面值构建的算术表达式、谓词表达式和函数表达式。您可以在不同子句中使用表达式，例如在 `Filter` 和 `Stats` 命令中使用算术表达式。

**运算符**

算术表达式是由数字字面值和二进制算术运算符组成的表达式，如下所示：

1. `+`：加。

1. `-`：减。

1. `*`：乘。

1. `/`：除（对于整数，结果为舍去小数部分的整数）

1. `%`：模运算（仅适用于整数；结果为除法的余数）

**优先级**

使用圆括号控制算术运算符的优先顺序。否则，优先级较高的运算符会首先执行。

**类型转换**

查找运算符签名时会执行隐式类型转换。例如，整数 `+` 实数符合签名 `+(double,double)` 的要求，其结果为实数。此规则也适用于函数调用。

不同类型算术表达式的示例：

```
os> source=accounts | where age > (25 + 5) | fields age ;
fetched rows / total rows = 3/3
+-------+
| age   |
|-------|
| 32    |
| 36    |
| 33    |
+-------+
```

**谓词运算符**  
谓词运算符是计算结果为 true 的表达式。`MISSING` 和 `NULL` 值比较遵循以下规则：
+ `MISSING` 值仅等于 `MISSING` 值，且小于其他值。
+ `NULL` 值等于 `NULL` 值，大于 `MISSING` 值，但小于所有其他值。

**运算符**


**谓词运算符**  

| Name | 说明 | 
| --- | --- | 
| > | 大于运算符 | 
| >= | 大于或等于运算符 | 
| < | 小于运算符 | 
| \$1= | 不等于运算符 | 
| <= | 小于或等于运算符 | 
| = | 等于运算符 | 
| LIKE | 简单模式匹配 | 
| IN | NULL 值测试 | 
| AND | AND 运算符 | 
| OR | OR 运算符 | 
| XOR | XOR 运算符 | 
| NOT | 非 NULL 值测试 | 

您可以比较日期时间。比较不同的日期时间类型（例如 `DATE` 和 `TIME`）时，两者均转换为 `DATETIME`。以下规则适用于转换：
+  `TIME` 适用于今日日期。
+ `DATE` 解释为在午夜。

**基本谓词运算符**  
比较运算符的示例：

```
os> source=accounts | where age > 33 | fields age ;
fetched rows / total rows = 1/1
+-------+
| age   |
|-------|
| 36    |
+-------+
```

**`IN`**  
值列表中 `IN` 运算符测试字段的示例：

```
os> source=accounts | where age in (32, 33) | fields age ;
fetched rows / total rows = 2/2
+-------+
| age   |
|-------|
| 32    |
| 33    |
+-------+
```

**`OR`**  
`OR` 运算符的示例：

```
os> source=accounts | where age = 32 OR age = 33 | fields age ;
fetched rows / total rows = 2/2
+-------+
| age   |
|-------|
| 32    |
| 33    |
+-------+
```

**`NOT`**  
`NOT` 运算符的示例：

```
os> source=accounts | where age not in (32, 33) | fields age ;
fetched rows / total rows = 2/2
+-------+
| age   |
|-------|
| 36    |
| 28    |
+-------+
```

##### PPL IP 地址函数
<a name="supported-ppl-ip-address-functions"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 功能，请参阅。[函数](#supported-ppl-functions)

##### `CIDRMATCH`
<a name="supported-ppl-address-functions-cidrmatch"></a>

**用法**：`CIDRMATCH(ip, cidr)` 检查指定的 IP 地址是否在给定的 cidr 范围内。

**参数类型：**
+ STRING、STRING
+ 返回类型：BOOLEAN

**示例**：

```
os> source=ips | where cidrmatch(ip, '***********/24') | fields ip
fetched rows / total rows = 1/1
+--------------+
| ip           |
|--------------|
| ***********  |
+--------------+

os> source=ipsv6 | where cidrmatch(ip, '2003:db8::/32') | fields ip
fetched rows / total rows = 1/1
+-----------------------------------------+
| ip                                      |
|-----------------------------------------|
| 2003:0db8:****:****:****:****:****:0000 |
+-----------------------------------------+
```

**注意**  
`ip`可以是 IPv4 或 IPv6地址。
`cidr`可以是一个 IPv4 或一个 IPv6方块。
`ip`并且`cidr`必须两者兼 IPv4 而有之 IPv6。
`ip` 和 `cidr` 必须同时满足有效且非空/非 null。

##### PPL JSON 函数
<a name="supported-ppl-json-functions"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 功能，请参阅。[函数](#supported-ppl-functions)

##### `JSON`
<a name="supported-ppl-json-functions-json"></a>

**用法**：`json(value)` 评估字符串是否可以解析为 JSON 格式。如果是有效 JSON，则该函数返回原始字符串；如果无效，则返回 null。

**参数类型**：STRING

**返回类型**：STRING/NULL。有效 JSON 对象格式的 STRING 表达式。

**示例：**

```
os> source=people | eval `valid_json()` = json('[1,2,3,{"f1":1,"f2":[5,6]},4]') | fields valid_json
fetched rows / total rows = 1/1
+---------------------------------+
| valid_json                      |
+---------------------------------+
| [1,2,3,{"f1":1,"f2":[5,6]},4]   |
+---------------------------------+

os> source=people | eval `invalid_json()` = json('{"invalid": "json"') | fields invalid_json
fetched rows / total rows = 1/1
+----------------+
| invalid_json   |
+----------------+
| null           |
+----------------+
```

##### `JSON_OBJECT`
<a name="supported-ppl-json-functions-json-object"></a>

**用法**：`json_object(<key>, <value>[, <key>, <value>]...)` 返回由键值对组成的 JSON 对象。

**参数类型：**
+ <key> 必须为 STRING。
+ <value> 可以是任何数据类型。

**返回类型**：JSON\$1OBJECT。有效 JSON 对象的 StructType 表达式。

**示例：**

```
os> source=people | eval result = json_object('key', 123.45) | fields result
fetched rows / total rows = 1/1
+------------------+
| result           |
+------------------+
| {"key":123.45}   |
+------------------+

os> source=people | eval result = json_object('outer', json_object('inner', 123.45)) | fields result
fetched rows / total rows = 1/1
+------------------------------+
| result                       |
+------------------------------+
| {"outer":{"inner":123.45}}   |
+------------------------------+
```

##### `JSON_ARRAY`
<a name="supported-ppl-json-functions-json-array"></a>

**用法**：`json_array(<value>...)` 使用值列表创建 JSON 数组。

**参数类型**：`<value>` 可以是任何类型的值，例如字符串、数字或布尔值。

**返回类型**：ARRAY。任何受支持数据类型的数组，用于表示有效的 JSON 数组。

**示例：**

```
os> source=people | eval `json_array` = json_array(1, 2, 0, -1, 1.1, -0.11)
fetched rows / total rows = 1/1
+------------------------------+
| json_array                   |
+------------------------------+
| [1.0,2.0,0.0,-1.0,1.1,-0.11] |
+------------------------------+

os> source=people | eval `json_array_object` = json_object("array", json_array(1, 2, 0, -1, 1.1, -0.11))
fetched rows / total rows = 1/1
+----------------------------------------+
| json_array_object                      |
+----------------------------------------+
| {"array":[1.0,2.0,0.0,-1.0,1.1,-0.11]} |
+----------------------------------------+
```

##### `TO_JSON_STRING`
<a name="supported-ppl-json-functions-to-json-string"></a>

**用法**：`to_json_string(jsonObject)` 返回包含给定 json 对象值的 JSON 字符串。

**参数类型**：JSON\$1OBJECT 

**返回类型**：STRING

**示例：**

```
os> source=people | eval `json_string` = to_json_string(json_array(1, 2, 0, -1, 1.1, -0.11)) | fields json_string
fetched rows / total rows = 1/1
+--------------------------------+
| json_string                    |
+--------------------------------+
| [1.0,2.0,0.0,-1.0,1.1,-0.11]   |
+--------------------------------+

os> source=people | eval `json_string` = to_json_string(json_object('key', 123.45)) | fields json_string
fetched rows / total rows = 1/1
+-----------------+
| json_string     |
+-----------------+
| {'key', 123.45} |
+-----------------+
```

##### `ARRAY_LENGTH`
<a name="supported-ppl-json-functions-array-length"></a>

**用法**：`array_length(jsonArray)` 返回最外层数组中的元素个数。

**参数类型**：ARRAY。ARRAY 或 JSON\$1ARRAY 对象。

**返回类型**：INTEGER

**示例**：

```
os> source=people | eval `json_array` = json_array_length(json_array(1,2,3,4)), `empty_array` = json_array_length(json_array())
fetched rows / total rows = 1/1
+--------------+---------------+
| json_array   | empty_array   |
+--------------+---------------+
| 4            | 0             |
+--------------+---------------+
```

##### `JSON_EXTRACT`
<a name="supported-ppl-json-functions-json-extract"></a>

**用法**：`json_extract(jsonStr, path)` 根据指定的 JSON 路径从 JSON 字符串中提取 JSON 对象。如果输入 JSON 字符串无效，则该函数返回 null。

**参数类型**：STRING、STRING

**返回类型**：STRING
+ 有效 JSON 对象格式的 STRING 表达式。
+ 如果 JSON 无效，则返回 `NULL`。

**示例：**

```
os> source=people | eval `json_extract('{"a":"b"}', '$.a')` = json_extract('{"a":"b"}', '$a')
fetched rows / total rows = 1/1
+----------------------------------+
| json_extract('{"a":"b"}', 'a')   |
+----------------------------------+
| b                                |
+----------------------------------+

os> source=people | eval `json_extract('{"a":[{"b":1},{"b":2}]}', '$.a[1].b')` = json_extract('{"a":[{"b":1},{"b":2}]}', '$.a[1].b')
fetched rows / total rows = 1/1
+-----------------------------------------------------------+
| json_extract('{"a":[{"b":1.0},{"b":2.0}]}', '$.a[1].b')   |
+-----------------------------------------------------------+
| 2.0                                                       |
+-----------------------------------------------------------+

os> source=people | eval `json_extract('{"a":[{"b":1},{"b":2}]}', '$.a[*].b')` = json_extract('{"a":[{"b":1},{"b":2}]}', '$.a[*].b')
fetched rows / total rows = 1/1
+-----------------------------------------------------------+
| json_extract('{"a":[{"b":1.0},{"b":2.0}]}', '$.a[*].b')   |
+-----------------------------------------------------------+
| [1.0,2.0]                                                 |
+-----------------------------------------------------------+

os> source=people | eval `invalid_json` = json_extract('{"invalid": "json"')
fetched rows / total rows = 1/1
+----------------+
| invalid_json   |
+----------------+
| null           |
+----------------+
```

##### `JSON_KEYS`
<a name="supported-ppl-json-functions-json-keys"></a>

**用法**：`json_keys(jsonStr)` 以数组形式返回最外层 JSON 对象的所有键。

**参数类型**：STRING。有效 JSON 对象格式的 STRING 表达式。

**返回类型**：ARRAY[STRING]。对于任何其他有效的 JSON 字符串、空字符串或无效的 JSON，该函数均返回 `NULL`。

**示例：**

```
os> source=people | eval `keys` = json_keys('{"f1":"abc","f2":{"f3":"a","f4":"b"}}')
fetched rows / total rows = 1/1
+------------+
| keus       |
+------------+
| [f1, f2]   |
+------------+

os> source=people | eval `keys` = json_keys('[1,2,3,{"f1":1,"f2":[5,6]},4]')
fetched rows / total rows = 1/1
+--------+
| keys   |
+--------+
| null   |
+--------+
```

##### `JSON_VALID`
<a name="supported-ppl-json-functions-json-valid"></a>

**用法**：`json_valid(jsonStr)` 评估 JSON 字符串是否使用有效的 JSON 语法并返回 TRUE 或 FALSE。

**参数类型**：STRING

**返回类型**：BOOLEAN

**示例：**

```
os> source=people | eval `valid_json` = json_valid('[1,2,3,4]'), `invalid_json` = json_valid('{"invalid": "json"') | feilds `valid_json`, `invalid_json`
fetched rows / total rows = 1/1
+--------------+----------------+
| valid_json   | invalid_json   |
+--------------+----------------+
| True         | False          |
+--------------+----------------+

os> source=accounts | where json_valid('[1,2,3,4]') and isnull(email) | fields account_number, email
fetched rows / total rows = 1/1
+------------------+---------+
| account_number   | email   |
|------------------+---------|
| 13               | null    |
+------------------+---------+
```

##### PPL Lambda 函数
<a name="supported-ppl-lambda-functions"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 功能，请参阅。[函数](#supported-ppl-functions)

##### `EXISTS`
<a name="supported-ppl-lambda-functions-exists"></a>

**用法**：`exists(array, lambda)` 评估 Lambda 谓词是否适用于数组中的一个或多个元素。

**参数类型**：ARRAY、LAMBDA

**返回类型**：BOOLEAN。如果数组中至少有一个元素满足 Lambda 谓词，则返回 `TRUE`，否则返回 `FALSE`。

**示例：**

```
 os> source=people | eval array = json_array(1, -1, 2), result = exists(array, x -> x > 0) | fields result
fetched rows / total rows = 1/1
+-----------+
| result    |
+-----------+
| true      |
+-----------+

os> source=people | eval array = json_array(-1, -3, -2), result = exists(array, x -> x > 0) | fields result
fetched rows / total rows = 1/1
+-----------+
| result    |
+-----------+
| false     |
+-----------+
```

##### `FILTER`
<a name="supported-ppl-lambda-functions-filter"></a>

**用法**：`filter(array, lambda)` 使用给定的 Lambda 函数筛选输入数组。

**参数类型**：ARRAY、LAMBDA

**返回类型**：ARRAY。ARRAY，包含输入数组中满足 lambda 谓词的所有元素。

**示例：**

```
 os> source=people | eval array = json_array(1, -1, 2), result = filter(array, x -> x > 0) | fields result
fetched rows / total rows = 1/1
+-----------+
| result    |
+-----------+
| [1, 2]    |
+-----------+

os> source=people | eval array = json_array(-1, -3, -2), result = filter(array, x -> x > 0) | fields result
fetched rows / total rows = 1/1
+-----------+
| result    |
+-----------+
| []        |
+-----------+
```

##### `TRANSFORM`
<a name="supported-ppl-lambda-functions-transform"></a>

**用法**：`transform(array, lambda)` 使用 Lambda 转换函数转换数组中的元素。如果使用二进制 Lambda 函数，则第二个参数表示元素的索引。这与函数式编程中的 `map` 类似。

**参数类型**：ARRAY、LAMBDA

**返回类型**：ARRAY。ARRAY，包含将 lambda 转换函数应用于输入数组中每个元素的结果。

**示例：**

```
os> source=people | eval array = json_array(1, 2, 3), result = transform(array, x -> x + 1) | fields result
fetched rows / total rows = 1/1
+--------------+
| result       |
+--------------+
| [2, 3, 4]    |
+--------------+

os> source=people | eval array = json_array(1, 2, 3), result = transform(array, (x, i) -> x + i) | fields result
fetched rows / total rows = 1/1
+--------------+
| result       |
+--------------+
| [1, 3, 5]    |
+--------------+
```

##### `REDUCE`
<a name="supported-ppl-lambda-functions-reduce"></a>

**用法**：`reduce(array, start, merge_lambda, finish_lambda)` 通过应用 lambda 函数将数组简化为单个值。该函数将 merge\$1lambda 应用于起始值和所有数组元素，然后将 `finish_lambda` 应用于结果。

**参数类型**：ARRAY、ANY、LAMBDA、LAMBDA

**返回类型**：ANY。将 Lambda 函数应用于起始值和输入数组后的最终结果。

**示例：**

```
 os> source=people | eval array = json_array(1, 2, 3), result = reduce(array, 0, (acc, x) -> acc + x) | fields result
fetched rows / total rows = 1/1
+-----------+
| result    |
+-----------+
| 6         |
+-----------+

os> source=people | eval array = json_array(1, 2, 3), result = reduce(array, 10, (acc, x) -> acc + x) | fields result
fetched rows / total rows = 1/1
+-----------+
| result    |
+-----------+
| 16        |
+-----------+

os> source=people | eval array = json_array(1, 2, 3), result = reduce(array, 0, (acc, x) -> acc + x, acc -> acc * 10) | fields result
fetched rows / total rows = 1/1
+-----------+
| result    |
+-----------+
| 60        |
+-----------+
```

##### PPL 数学函数
<a name="supported-ppl-math-functions"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 功能，请参阅。[函数](#supported-ppl-functions)

##### `ABS`
<a name="supported-ppl-math-functions-abs"></a>

**用法**：`ABS(x) ` 计算 x 的绝对值。

**参数类型：**INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**INTEGER/LONG/FLOAT/DOUBLE

**示例**：

```
os> source=people | eval `ABS(-1)` = ABS(-1) | fields `ABS(-1)`
fetched rows / total rows = 1/1
+-----------+
| ABS(-1)   |
|-----------|
| 1         |
+-----------+
```

##### `ACOS`
<a name="supported-ppl-math-functions-acos"></a>

**用法**：`ACOS(x)` 计算 x 的反余弦值。如果 x 不在 -1 到 1 的范围内，则返回 `NULL`。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `ACOS(0)` = ACOS(0) | fields `ACOS(0)`
fetched rows / total rows = 1/1
+--------------------+
| ACOS(0)            |
|--------------------|
| 1.5707963267948966 |
+--------------------+
```

##### `ASIN`
<a name="supported-ppl-math-functions-asin"></a>

**用法**：`asin(x)` 计算 x 的反正弦值。如果 x 不在 -1 到 1 的范围内，则返回 `NULL`。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `ASIN(0)` = ASIN(0) | fields `ASIN(0)`
fetched rows / total rows = 1/1
+-----------+
| ASIN(0)   |
|-----------|
| 0.0       |
+-----------+
```

##### `ATAN`
<a name="supported-ppl-math-functions-atan"></a>

**用法**：`ATAN(x)` 计算 x 的反正切值。`atan(y, x)` 计算 y/x 的反正切值，唯一的不同在于两个参数的符号决定结果的象限位置。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `ATAN(2)` = ATAN(2), `ATAN(2, 3)` = ATAN(2, 3) | fields `ATAN(2)`, `ATAN(2, 3)`
fetched rows / total rows = 1/1
+--------------------+--------------------+
| ATAN(2)            | ATAN(2, 3)         |
|--------------------+--------------------|
| 1.1071487177940904 | 0.5880026035475675 |
+--------------------+--------------------+
```

##### `ATAN2`
<a name="supported-ppl-math-functions-atan2"></a>

**用法**：`ATAN2(y, x)` 计算 y/x 的反正切值，唯一的不同在于两个参数的符号决定结果的象限位置。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `ATAN2(2, 3)` = ATAN2(2, 3) | fields `ATAN2(2, 3)`
fetched rows / total rows = 1/1
+--------------------+
| ATAN2(2, 3)        |
|--------------------|
| 0.5880026035475675 |
+--------------------+
```

##### `CBRT`
<a name="supported-ppl-math-functions-cbrt"></a>

**用法**：`CBRT` 计算数字的立方根。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型**：DOUBLE：

INTEGER/LONG/FLOAT/DOUBLE-> 双打

**示例**：

```
opensearchsql> source=location | eval `CBRT(8)` = CBRT(8), `CBRT(9.261)` = CBRT(9.261), `CBRT(-27)` = CBRT(-27) | fields `CBRT(8)`, `CBRT(9.261)`, `CBRT(-27)`;
fetched rows / total rows = 2/2
+-----------+---------------+-------------+
| CBRT(8)   | CBRT(9.261)   | CBRT(-27)   |
|-----------+---------------+-------------|
| 2.0       | 2.1           | -3.0        |
| 2.0       | 2.1           | -3.0        |
+-----------+---------------+-------------+
```

##### `CEIL`
<a name="supported-ppl-math-functions-ceil"></a>

**用法**：`CEILING` 函数的别名。`CEILING(T)` 取值上限为 T。

**限制**：仅当 IEEE 754 双精度类型在存储时显示十进制数时，`CEILING` 才会按预期工作。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型**：LONG

**示例**：

```
os> source=people | eval `CEILING(0)` = CEILING(0), `CEILING(50.00005)` = CEILING(50.00005), `CEILING(-50.00005)` = CEILING(-50.00005) | fields `CEILING(0)`, `CEILING(50.00005)`, `CEILING(-50.00005)`
fetched rows / total rows = 1/1
+--------------+---------------------+----------------------+
| CEILING(0)   | CEILING(50.00005)   | CEILING(-50.00005)   |
|--------------+---------------------+----------------------|
| 0            | 51                  | -50                  |
+--------------+---------------------+----------------------+

os> source=people | eval `CEILING(3147483647.12345)` = CEILING(3147483647.12345), `CEILING(113147483647.12345)` = CEILING(113147483647.12345), `CEILING(3147483647.00001)` = CEILING(3147483647.00001) | fields `CEILING(3147483647.12345)`, `CEILING(113147483647.12345)`, `CEILING(3147483647.00001)`
fetched rows / total rows = 1/1
+-----------------------------+-------------------------------+-----------------------------+
| CEILING(3147483647.12345)   | CEILING(113147483647.12345)   | CEILING(3147483647.00001)   |
|-----------------------------+-------------------------------+-----------------------------|
| 3147483648                  | 113147483648                  | 3147483648                  |
+-----------------------------+-------------------------------+-----------------------------+
```

##### `CONV`
<a name="supported-ppl-math-functions-conv"></a>

**用法**：`CONV(x, a, b)` 将数字 x 从 a 基数转换为 b 基数。

**参数类型**：x：STRING，a：INTEGER，b：INTEGER

**返回类型**：STRING

**示例**：

```
os> source=people | eval `CONV('12', 10, 16)` = CONV('12', 10, 16), `CONV('2C', 16, 10)` = CONV('2C', 16, 10), `CONV(12, 10, 2)` = CONV(12, 10, 2), `CONV(1111, 2, 10)` = CONV(1111, 2, 10) | fields `CONV('12', 10, 16)`, `CONV('2C', 16, 10)`, `CONV(12, 10, 2)`, `CONV(1111, 2, 10)`
fetched rows / total rows = 1/1
+----------------------+----------------------+-------------------+---------------------+
| CONV('12', 10, 16)   | CONV('2C', 16, 10)   | CONV(12, 10, 2)   | CONV(1111, 2, 10)   |
|----------------------+----------------------+-------------------+---------------------|
| c                    | 44                   | 1100              | 15                  |
+----------------------+----------------------+-------------------+---------------------+
```

##### `COS`
<a name="supported-ppl-math-functions-cos"></a>

**用法**：`COS(x)` 计算 x 的余弦值，其中 x 的单位是弧度。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `COS(0)` = COS(0) | fields `COS(0)`
fetched rows / total rows = 1/1
+----------+
| COS(0)   |
|----------|
| 1.0      |
+----------+
```

##### `COT`
<a name="supported-ppl-math-functions-cot"></a>

**用法**：`COT(x)` 计算 x 的余切值。如果 x 等于 0，则返回 out-of-range错误。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `COT(1)` = COT(1) | fields `COT(1)`
fetched rows / total rows = 1/1
+--------------------+
| COT(1)             |
|--------------------|
| 0.6420926159343306 |
+--------------------+
```

##### `CRC32`
<a name="supported-ppl-math-functions-crc32"></a>

**用法**：`CRC32` 计算循环冗余校验值，并返回 32 位无符号值。

**参数类型**：STRING

**返回类型**：LONG

**示例**：

```
os> source=people | eval `CRC32('MySQL')` = CRC32('MySQL') | fields `CRC32('MySQL')`
fetched rows / total rows = 1/1
+------------------+
| CRC32('MySQL')   |
|------------------|
| 3259397556       |
+------------------+
```

##### `DEGREES`
<a name="supported-ppl-math-functions-degrees"></a>

**用法**：`DEGREES(x)` 将 x 的单位从弧度转换为度。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `DEGREES(1.57)` = DEGREES(1.57) | fields `DEGREES(1.57)`
fetched rows / total rows  = 1/1
+-------------------+
| DEGREES(1.57)     |
|-------------------|
| 89.95437383553924 |
+-------------------+
```

##### `E`
<a name="supported-ppl-math-functions-e"></a>

**用法**：`E()` 返回欧拉数字。

**返回类型**：DOUBLE

**示例**：

```
os> source=people | eval `E()` = E() | fields `E()`
fetched rows / total rows = 1/1
+-------------------+
| E()               |
|-------------------|
| 2.718281828459045 |
+-------------------+
```

##### `EXP`
<a name="supported-ppl-math-functions-exp"></a>

**用法**：`EXP(x)` 返回 e 的 x 次方。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `EXP(2)` = EXP(2) | fields `EXP(2)`
fetched rows / total rows = 1/1
+------------------+
| EXP(2)           |
|------------------|
| 7.38905609893065 |
+------------------+
```

##### `FLOOR`
<a name="supported-ppl-math-functions-floor"></a>

**用法**：`FLOOR(T)` 取值下限为 T。

**限制**：仅当 IEEE 754 双精度类型在存储时显示十进制数时，`FLOOR` 才会按预期工作。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型**：LONG

**示例**：

```
os> source=people | eval `FLOOR(0)` = FLOOR(0), `FLOOR(50.00005)` = FLOOR(50.00005), `FLOOR(-50.00005)` = FLOOR(-50.00005) | fields `FLOOR(0)`, `FLOOR(50.00005)`, `FLOOR(-50.00005)`
fetched rows / total rows = 1/1
+------------+-------------------+--------------------+
| FLOOR(0)   | FLOOR(50.00005)   | FLOOR(-50.00005)   |
|------------+-------------------+--------------------|
| 0          | 50                | -51                |
+------------+-------------------+--------------------+

os> source=people | eval `FLOOR(3147483647.12345)` = FLOOR(3147483647.12345), `FLOOR(113147483647.12345)` = FLOOR(113147483647.12345), `FLOOR(3147483647.00001)` = FLOOR(3147483647.00001) | fields `FLOOR(3147483647.12345)`, `FLOOR(113147483647.12345)`, `FLOOR(3147483647.00001)`
fetched rows / total rows = 1/1
+---------------------------+-----------------------------+---------------------------+
| FLOOR(3147483647.12345)   | FLOOR(113147483647.12345)   | FLOOR(3147483647.00001)   |
|---------------------------+-----------------------------+---------------------------|
| 3147483647                | 113147483647                | 3147483647                |
+---------------------------+-----------------------------+---------------------------+

os> source=people | eval `FLOOR(282474973688888.022)` = FLOOR(282474973688888.022), `FLOOR(9223372036854775807.022)` = FLOOR(9223372036854775807.022), `FLOOR(9223372036854775807.0000001)` = FLOOR(9223372036854775807.0000001) | fields `FLOOR(282474973688888.022)`, `FLOOR(9223372036854775807.022)`, `FLOOR(9223372036854775807.0000001)`
fetched rows / total rows = 1/1
+------------------------------+----------------------------------+--------------------------------------+
| FLOOR(282474973688888.022)   | FLOOR(9223372036854775807.022)   | FLOOR(9223372036854775807.0000001)   |
|------------------------------+----------------------------------+--------------------------------------|
| 282474973688888              | 9223372036854775807              | 9223372036854775807                  |
+------------------------------+----------------------------------+--------------------------------------+
```

##### `LN`
<a name="supported-ppl-math-functions-ln"></a>

**用法**：`LN(x)` 返回 x 的自然对数。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `LN(2)` = LN(2) | fields `LN(2)`
fetched rows / total rows = 1/1
+--------------------+
| LN(2)              |
|--------------------|
| 0.6931471805599453 |
+--------------------+
```

##### `LOG`
<a name="supported-ppl-math-functions-log"></a>

**用法**：`LOG(x)` 返回 x 的自然对数，即以 e 为底 x 的对数。log(B, x) 等同于 log(x)/log(B)。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `LOG(2)` = LOG(2), `LOG(2, 8)` = LOG(2, 8) | fields `LOG(2)`, `LOG(2, 8)`
fetched rows / total rows = 1/1
+--------------------+-------------+
| LOG(2)             | LOG(2, 8)   |
|--------------------+-------------|
| 0.6931471805599453 | 3.0         |
+--------------------+-------------+
```

##### `LOG2`
<a name="supported-ppl-math-functions-log2"></a>

**用法**：`LOG2(x)` 等同于 `log(x)`/`log(2)`。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `LOG2(8)` = LOG2(8) | fields `LOG2(8)`
fetched rows / total rows = 1/1
+-----------+
| LOG2(8)   |
|-----------|
| 3.0       |
+-----------+
```

##### `LOG10`
<a name="supported-ppl-math-functions-log10"></a>

**用法**：`LOG10(x)` 等同于 `log(x)`/`log(10)`。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `LOG10(100)` = LOG10(100) | fields `LOG10(100)`
fetched rows / total rows = 1/1
+--------------+
| LOG10(100)   |
|--------------|
| 2.0          |
+--------------+
```

##### `MOD`
<a name="supported-ppl-math-functions-mod"></a>

**用法**：`MOD(n, m)` 计算数字 n 除以 m 的余数。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型**：如果 m 为非零值，则在 n 和 m 的类型之间使用宽类型。如果 m 等于 0，则返回 NULL。

**示例**：

```
os> source=people | eval `MOD(3, 2)` = MOD(3, 2), `MOD(3.1, 2)` = MOD(3.1, 2) | fields `MOD(3, 2)`, `MOD(3.1, 2)`
fetched rows / total rows = 1/1
+-------------+---------------+
| MOD(3, 2)   | MOD(3.1, 2)   |
|-------------+---------------|
| 1           | 1.1           |
+-------------+---------------+
```

##### `PI`
<a name="supported-ppl-math-functions-pi"></a>

**用法**：`PI() ` 返回常量 pi。

**返回类型**：DOUBLE

**示例**：

```
os> source=people | eval `PI()` = PI() | fields `PI()`
fetched rows / total rows = 1/1
+-------------------+
| PI()              |
|-------------------|
| 3.141592653589793 |
+-------------------+
```

##### `POW`
<a name="supported-ppl-math-functions-pow"></a>

**用法**：`POW(x, y)` 计算 x 的 y 次幂的值。错误输入会返回 `NULL` 结果。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型**：DOUBLE

**同义词**：`POWER(_, _)`

**示例**：

```
os> source=people | eval `POW(3, 2)` = POW(3, 2), `POW(-3, 2)` = POW(-3, 2), `POW(3, -2)` = POW(3, -2) | fields `POW(3, 2)`, `POW(-3, 2)`, `POW(3, -2)`
fetched rows / total rows = 1/1
+-------------+--------------+--------------------+
| POW(3, 2)   | POW(-3, 2)   | POW(3, -2)         |
|-------------+--------------+--------------------|
| 9.0         | 9.0          | 0.1111111111111111 |
+-------------+--------------+--------------------+
```

##### POWER
<a name="supported-ppl-math-functions-power"></a>

**用法**：`POWER(x, y)` 计算 x 的 y 次幂的值。错误输入会返回 `NULL` 结果。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型**：DOUBLE

**同义词**：`POW(_, _)`

**示例**：

```
os> source=people | eval `POWER(3, 2)` = POWER(3, 2), `POWER(-3, 2)` = POWER(-3, 2), `POWER(3, -2)` = POWER(3, -2) | fields `POWER(3, 2)`, `POWER(-3, 2)`, `POWER(3, -2)`
fetched rows / total rows = 1/1
+---------------+----------------+--------------------+
| POWER(3, 2)   | POWER(-3, 2)   | POWER(3, -2)       |
|---------------+----------------+--------------------|
| 9.0           | 9.0            | 0.1111111111111111 |
+---------------+----------------+--------------------+
```

##### `RADIANS`
<a name="supported-ppl-math-functions-radians"></a>

**用法**：`RADIANS(x)` 将 x 的单位从度转换为弧度。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `RADIANS(90)` = RADIANS(90) | fields `RADIANS(90)`
fetched rows / total rows  = 1/1
+--------------------+
| RADIANS(90)        |
|--------------------|
| 1.5707963267948966 |
+--------------------+
```

##### `RAND`
<a name="supported-ppl-math-functions-rand"></a>

**用法**：`RAND()`/`RAND(N)` 返回 0 <= 值 < 1.0 范围内的随机浮点数值。如果指定整数 N，该函数将在执行前初始化种子值。这种行为的一种含义是，使用相同的参数 N 时，`rand(N)` 每次都会返回相同的值，从而生成可重复的列值序列。

**参数类型**：INTEGER

**返回类型**：FLOAT

**示例**：

```
os> source=people | eval `RAND(3)` = RAND(3) | fields `RAND(3)`
fetched rows / total rows = 1/1
+------------+
| RAND(3)    |
|------------|
| 0.73105735 |
+------------+
```

##### `ROUND`
<a name="supported-ppl-math-functions-round"></a>

**用法**：`ROUND(x, d)` 将参数 x 四舍五入到 d 位小数。如果未指定 d，则默认值为 0。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型映射**：
+ (INTEGER/LONG [,INTEGER]) -> LONG
+ (FLOAT/DOUBLE [,INTEGER]) -> LONG

**示例**：

```
os> source=people | eval `ROUND(12.34)` = ROUND(12.34), `ROUND(12.34, 1)` = ROUND(12.34, 1), `ROUND(12.34, -1)` = ROUND(12.34, -1), `ROUND(12, 1)` = ROUND(12, 1) | fields `ROUND(12.34)`, `ROUND(12.34, 1)`, `ROUND(12.34, -1)`, `ROUND(12, 1)`
fetched rows / total rows = 1/1
+----------------+-------------------+--------------------+----------------+
| ROUND(12.34)   | ROUND(12.34, 1)   | ROUND(12.34, -1)   | ROUND(12, 1)   |
|----------------+-------------------+--------------------+----------------|
| 12.0           | 12.3              | 10.0               | 12             |
+----------------+-------------------+--------------------+----------------+
```

##### `SIGN`
<a name="supported-ppl-math-functions-sign"></a>

**用法**：`SIGN` 返回参数的符号值，为 -1、0 或 1，取决于该数值是负数、零还是正数。

**参数类型**：INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**INTEGER

**示例**：

```
os> source=people | eval `SIGN(1)` = SIGN(1), `SIGN(0)` = SIGN(0), `SIGN(-1.1)` = SIGN(-1.1) | fields `SIGN(1)`, `SIGN(0)`, `SIGN(-1.1)`
fetched rows / total rows = 1/1
+-----------+-----------+--------------+
| SIGN(1)   | SIGN(0)   | SIGN(-1.1)   |
|-----------+-----------+--------------|
| 1         | 0         | -1           |
+-----------+-----------+--------------+
```

##### `SIN`
<a name="supported-ppl-math-functions-sin"></a>

**用法**：`sin(x)` 计算 x 的正弦值，其中 x 的单位是弧度。

**参数类型：**INTEGER/LONG/FLOAT/DOUBLE

**返回类型：**DOUBLE

**示例**：

```
os> source=people | eval `SIN(0)` = SIN(0) | fields `SIN(0)`
fetched rows / total rows = 1/1
+----------+
| SIN(0)   |
|----------|
| 0.0      |
+----------+
```

##### `SQRT`
<a name="supported-ppl-math-functions-sqrt"></a>

**用法**：`SQRT` 计算非负数的平方根。

**参数类型：**INTEGER/LONG/FLOAT/DOUBLE

**返回类型映射：**
+ （非负数）INTEGER/LONG/FLOAT/DOUBLE-> 双精度
+ （负数）INTEGER/LONG/FLOAT/DOUBLE-> 空

**示例**：

```
os> source=people | eval `SQRT(4)` = SQRT(4), `SQRT(4.41)` = SQRT(4.41) | fields `SQRT(4)`, `SQRT(4.41)`
fetched rows / total rows = 1/1
+-----------+--------------+
| SQRT(4)   | SQRT(4.41)   |
|-----------+--------------|
| 2.0       | 2.1          |
+-----------+--------------+
```

##### PPL 字符串函数
<a name="supported-ppl-string-functions"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 功能，请参阅。[函数](#supported-ppl-functions)

##### `CONCAT`
<a name="supported-ppl-string-functions-concat"></a>

**用法**：`CONCAT(str1, str2, ...., str_9)` 最多可合并 9 个字符串。

**参数类型：**
+ STRING、STRING、....、STRING
+ 返回类型：STRING

**示例**：

```
os> source=people | eval `CONCAT('hello', 'world')` = CONCAT('hello', 'world'), `CONCAT('hello ', 'whole ', 'world', '!')` = CONCAT('hello ', 'whole ', 'world', '!') | fields `CONCAT('hello', 'world')`, `CONCAT('hello ', 'whole ', 'world', '!')`
fetched rows / total rows = 1/1
+----------------------------+--------------------------------------------+
| CONCAT('hello', 'world')   | CONCAT('hello ', 'whole ', 'world', '!')   |
|----------------------------+--------------------------------------------|
| helloworld                 | hello whole world!                         |
+----------------------------+--------------------------------------------+
```

##### `CONCAT_WS`
<a name="supported-ppl-string-functions-concat-ws"></a>

**用法**：`CONCAT_WS(sep, str1, str2)` 使用指定的分隔符连接两个或多个字符串。

**参数类型：**
+ STRING、STRING、....、STRING
+ 返回类型：STRING

**示例**：

```
os> source=people | eval `CONCAT_WS(',', 'hello', 'world')` = CONCAT_WS(',', 'hello', 'world') | fields `CONCAT_WS(',', 'hello', 'world')`
fetched rows / total rows = 1/1
+------------------------------------+
| CONCAT_WS(',', 'hello', 'world')   |
|------------------------------------|
| hello,world                        |
+------------------------------------+
```

##### `LENGTH`
<a name="supported-ppl-string-functions-length"></a>

**用法**：`length(str)` 返回输入字符串的长度，以字节为单位。

**参数类型：**
+ string
+ 返回类型：INTEGER

**示例**：

```
os> source=people | eval `LENGTH('helloworld')` = LENGTH('helloworld') | fields `LENGTH('helloworld')`
fetched rows / total rows = 1/1
+------------------------+
| LENGTH('helloworld')   |
|------------------------|
| 10                     |
+------------------------+
```

##### `LOWER`
<a name="supported-ppl-string-functions-lower"></a>

**用法**：`lower(string)` 将输入字符串转换为小写。

**参数类型：**
+ string
+ 返回类型：STRING

**示例**：

```
os> source=people | eval `LOWER('helloworld')` = LOWER('helloworld'), `LOWER('HELLOWORLD')` = LOWER('HELLOWORLD') | fields `LOWER('helloworld')`, `LOWER('HELLOWORLD')`
fetched rows / total rows = 1/1
+-----------------------+-----------------------+
| LOWER('helloworld')   | LOWER('HELLOWORLD')   |
|-----------------------+-----------------------|
| helloworld            | helloworld            |
+-----------------------+-----------------------+
```

##### `LTRIM`
<a name="supported-ppl-string-functions-ltrim"></a>

**用法**：`ltrim(str)` 删除输入字符串中的首空格字符。

**参数类型：**
+ string
+ 返回类型：STRING

**示例**：

```
os> source=people | eval `LTRIM('   hello')` = LTRIM('   hello'), `LTRIM('hello   ')` = LTRIM('hello   ') | fields `LTRIM('   hello')`, `LTRIM('hello   ')`
fetched rows / total rows = 1/1
+---------------------+---------------------+
| LTRIM('   hello')   | LTRIM('hello   ')   |
|---------------------+---------------------|
| hello               | hello               |
+---------------------+---------------------+
```

##### `POSITION`
<a name="supported-ppl-string-functions-position"></a>

**用法**：`POSITION(substr IN str)` 返回字符串中子字符串首次出现的位置。如果在 string 中未找到 substring，则返回 0。如果任何参数为 NULL，则返回 NULL。

**参数类型：**
+ STRING、STRING
+ 返回类型 INTEGER

**示例**：

```
os> source=people | eval `POSITION('world' IN 'helloworld')` = POSITION('world' IN 'helloworld'), `POSITION('invalid' IN 'helloworld')`= POSITION('invalid' IN 'helloworld')  | fields `POSITION('world' IN 'helloworld')`, `POSITION('invalid' IN 'helloworld')`
fetched rows / total rows = 1/1
+-------------------------------------+---------------------------------------+
| POSITION('world' IN 'helloworld')   | POSITION('invalid' IN 'helloworld')   |
|-------------------------------------+---------------------------------------|
| 6                                   | 0                                     |
+-------------------------------------+---------------------------------------+
```

##### `REVERSE`
<a name="supported-ppl-string-functions-reverse"></a>

**用法**：`REVERSE(str)` 返回输入字符串的反向字符串。

**参数类型：**
+ string
+ 返回类型：STRING

**示例**：

```
os> source=people | eval `REVERSE('abcde')` = REVERSE('abcde') | fields `REVERSE('abcde')`
fetched rows / total rows = 1/1
+--------------------+
| REVERSE('abcde')   |
|--------------------|
| edcba              |
+--------------------+
```

##### `RIGHT`
<a name="supported-ppl-string-functions-right"></a>

**用法**：`right(str, len)` 返回输入字符串中最右侧的字符。如果在 string 中未找到 substring，则返回 0。如果任何参数为 NULL，则返回 NULL。

**参数类型：**
+ STRING、INTEGER
+ 返回类型：STRING

**示例**：

```
os> source=people | eval `RIGHT('helloworld', 5)` = RIGHT('helloworld', 5), `RIGHT('HELLOWORLD', 0)` = RIGHT('HELLOWORLD', 0) | fields `RIGHT('helloworld', 5)`, `RIGHT('HELLOWORLD', 0)`
fetched rows / total rows = 1/1
+--------------------------+--------------------------+
| RIGHT('helloworld', 5)   | RIGHT('HELLOWORLD', 0)   |
|--------------------------+--------------------------|
| world                    |                          |
+--------------------------+--------------------------+
```

##### `RTRIM`
<a name="supported-ppl-string-functions-rtrim"></a>

**用法**：`rtrim(str)` 删除输入字符串中的尾随空格字符。

**参数类型：**
+ string
+ 返回类型：**STRING**

**示例**：

```
os> source=people | eval `RTRIM('   hello')` = RTRIM('   hello'), `RTRIM('hello   ')` = RTRIM('hello   ') | fields `RTRIM('   hello')`, `RTRIM('hello   ')`
fetched rows / total rows = 1/1
+---------------------+---------------------+
| RTRIM('   hello')   | RTRIM('hello   ')   |
|---------------------+---------------------|
|    hello            | hello               |
+---------------------+---------------------+
```

##### `SUBSTRING`
<a name="supported-ppl-string-functions-substring"></a>

**用法**：`substring(str, start)` 或 `substring(str, start, length)` 返回输入字符串的子字符串。如果未指定长度，则返回从起始位置算起的整个字符串。

**参数类型：**
+ STRING、INTEGER、INTEGER
+ 返回类型：STRING

**示例**：

```
os> source=people | eval `SUBSTRING('helloworld', 5)` = SUBSTRING('helloworld', 5), `SUBSTRING('helloworld', 5, 3)` = SUBSTRING('helloworld', 5, 3) | fields `SUBSTRING('helloworld', 5)`, `SUBSTRING('helloworld', 5, 3)`
fetched rows / total rows = 1/1
+------------------------------+---------------------------------+
| SUBSTRING('helloworld', 5)   | SUBSTRING('helloworld', 5, 3)   |
|------------------------------+---------------------------------|
| oworld                       | owo                             |
+------------------------------+---------------------------------+
```

##### `TRIM`
<a name="supported-ppl-string-functions-trim"></a>

**用法**：`trim(string)` 删除输入字符串中的首空格和尾随空格。

**参数类型：**
+ string
+ 返回类型：**STRING**

**示例**：

```
os> source=people | eval `TRIM('   hello')` = TRIM('   hello'), `TRIM('hello   ')` = TRIM('hello   ') | fields `TRIM('   hello')`, `TRIM('hello   ')`
fetched rows / total rows = 1/1
+--------------------+--------------------+
| TRIM('   hello')   | TRIM('hello   ')   |
|--------------------+--------------------|
| hello              | hello              |
+--------------------+--------------------+
```

##### `UPPER`
<a name="supported-ppl-string-functions-upper"></a>

**用法**：`upper(string)` 将输入字符串转换为大写。

**参数类型：**
+ string
+ 返回类型：STRING

**示例**：

```
os> source=people | eval `UPPER('helloworld')` = UPPER('helloworld'), `UPPER('HELLOWORLD')` = UPPER('HELLOWORLD') | fields `UPPER('helloworld')`, `UPPER('HELLOWORLD')`
fetched rows / total rows = 1/1
+-----------------------+-----------------------+
| UPPER('helloworld')   | UPPER('HELLOWORLD')   |
|-----------------------+-----------------------|
| HELLOWORLD            | HELLOWORLD            |
+-----------------------+-----------------------+
```

##### PPL 类型转换函数
<a name="supported-ppl-type-conversion-functions"></a>

**注意**  
要查看哪些 AWS 数据源集成支持此 PPL 功能，请参阅。[函数](#supported-ppl-functions)

##### `TRIM`
<a name="supported-ppl-conversion-functions-cast"></a>

**用法**：`cast(expr as dateType)` 将 `expr` 转换为 `dataType`，并返回 `dataType` 的值。

以下转换规则适用：


**类型转换规则**  

| Src/Target | string | NUMBER | BOOLEAN | TIMESTAMP | DATE | TIME | 
| --- | --- | --- | --- | --- | --- | --- | 
| string |  | Note1 | Note1 | TIMESTAMP() | DATE() | TIME() | 
| NUMBER | Note1 |  | v\$1=0 | 不适用 | 不适用 | 不适用 | 
| BOOLEAN | Note1 | v?1:0 |  | 不适用 | 不适用 | 不适用 | 
| TIMESTAMP | Note1 | 不适用 | 不适用 |  | DATE() | TIME() | 
| DATE | Note1 | 不适用 | 不适用 | 不适用 |  | 不适用 | 
| TIME | Note1 | 不适用 | 不适用 | 不适用 | 不适用 |  | 

**转换为字符串示例：**

```
os> source=people | eval `cbool` = CAST(true as string), `cint` = CAST(1 as string), `cdate` = CAST(CAST('2012-08-07' as date) as string) | fields `cbool`, `cint`, `cdate`
fetched rows / total rows = 1/1
+---------+--------+------------+
| cbool   | cint   | cdate      |
|---------+--------+------------|
| true    | 1      | 2012-08-07 |
+---------+--------+------------+
```

**转换为数字示例：**

```
os> source=people | eval `cbool` = CAST(true as int), `cstring` = CAST('1' as int) | fields `cbool`, `cstring`
fetched rows / total rows = 1/1
+---------+-----------+
| cbool   | cstring   |
|---------+-----------|
| 1       | 1         |
+---------+-----------+
```

**转换为日期示例：**

```
os> source=people | eval `cdate` = CAST('2012-08-07' as date), `ctime` = CAST('01:01:01' as time), `ctimestamp` = CAST('2012-08-07 01:01:01' as timestamp) | fields `cdate`, `ctime`, `ctimestamp`
fetched rows / total rows = 1/1
+------------+----------+---------------------+
| cdate      | ctime    | ctimestamp          |
|------------+----------+---------------------|
| 2012-08-07 | 01:01:01 | 2012-08-07 01:01:01 |
+------------+----------+---------------------+
```

**链式转换示例：**

```
os> source=people | eval `cbool` = CAST(CAST(true as string) as boolean) | fields `cbool`
fetched rows / total rows = 1/1
+---------+
| cbool   |
|---------|
| True    |
+---------+
```