# **SELECT**

构造一个子查询，可以是单行子查询作为结果集的一部分，也可以在in和exists操作符后面构成过滤条件。

## 语法{#grammar}

SELECT(**exp**,**where**)

- **exp**：必需。是一个模型的名称、模型的字段引用。
- **where**： 必需。表示关联关系表达式和条件过滤表达式。

## 用途

1. 作为计算字段使用，`exp`只能是单个字段或表达式，且必须是是单行子查询。
2. 与in操作符构成过滤条件，`exp`可以是单个字段或多字段数组。
3. 与exists操作符构成过滤条件，`exp`必须是表名，如果`where`中没有关联关系，则取全局关联关系。

## 示例{#examples}

1. `select([企业信息].[企业名称], [发票表].[销方]=[企业信息].[纳税人识别号])` 用于单字段，查询销方的企业名称等相关信息。
2. `select(count([发票表].[发票编码]), [发票表].[销方]=[企业信息].[纳税人识别号])` 用于单字段，查询各个企业的开局发票总数。
3. `[发票表].[销方] in select([企业信息].[ID], [企业信息].[失信]='Y')`  过滤出销方是失信企业的相关信息。
4. `exists select([发票表], [企业信息].[ID]=[发票表].[销方企业] and [企业信息].[失信]='Y')` 过滤出失信企业开具的发票信息。
5. `exists select([变更表], [企业信息].[ID]=[变更表].[ID] and [变更表].[变更类型]='法人变更')` 过滤出发生企业法人发生变更的企业。
6. `arr([发票表].[发票号码], [发票表].[发票代码]) in select(arr([逃税预警].[发票号码], [逃税预警].[发票代码]), [逃税预警].[逃税类型]=9)` 过滤出逃税预警的发票信息，这是一个`多字段`的in条件。

## 案例分析

查询需求：
对企业信息的查询，可以添加各种查询条件，如果企业是投资企业，则统计其总投资额。

分析：
`[企业投资关系]`中，一个企业可以投资多个企业，也可以被多个企业投资，是一个多对多的关系的对应表。
如果用常规分析方法，需要先从`[企业投资关系]`中统计出投资企业的投资总额，然后关联`[企业基本信息]`，需要一个加工。

新的思路：
使用系统提供的selelct函数和exists进行统计和过滤。

企业基本信息中加一个计算字段：
投资总额=`select(sum([企业投资关系].[认缴出资金额]),[企业投资关系].[投资企业ID]=[企业ID])`

表示从`[企业投资关系]`中统计投资金额，和企业表的关系是`[企业投资关系].[投资企业ID]=[企业ID]`。

如果需要过滤出所有投资企业，则可以通过exists过滤：
`EXISTS select([企业投资关系].[被投资企业ID],[企业投资关系].[投资企业ID]=[企业基本信息].[企业ID])`
