Azure Cosmos DB 的 SQL 子查询示例SQL subquery examples for Azure Cosmos DB

适用于: SQL API

子查询是嵌套在另一个查询中的查询。A subquery is a query nested within another query. 子查询也称为内部查询或内部选择。A subquery is also called an inner query or inner select. 包含子查询的语句通常称为外部查询。The statement that contains a subquery is typically called an outer query.

本文介绍 Azure Cosmos DB 中的 SQL 子查询及其常见用例。This article describes SQL subqueries and their common use cases in Azure Cosmos DB. 本文档中的所有示例查询都可以针对预加载在 Azure Cosmos DB 查询操场上的营养数据集运行。All sample queries in this doc can be run against a nutrition dataset that is preloaded on the Azure Cosmos DB Query Playground.

子查询的类型Types of subqueries

有两种主要类型的子查询:There are two main types of subqueries:

  • 相关:引用外部查询中的值的子查询。Correlated: A subquery that references values from the outer query. 将针对外部查询处理的每个行求值该子查询一次。The subquery is evaluated once for each row that the outer query processes.
  • 非相关:独立于外部查询的子查询。Non-correlated: A subquery that's independent of the outer query. 它可以独立运行,而不依赖于外部查询。It can be run on its own without relying on the outer query.

备注

Azure Cosmos DB 仅支持相关子查询。Azure Cosmos DB supports only correlated subqueries.

可以根据子查询返回的行数和列数进一步分类子查询。Subqueries can be further classified based on the number of rows and columns that they return. 有三种类型:There are three types:

  • Table:返回多个行和多个列。Table: Returns multiple rows and multiple columns.
  • 多值:返回多个行和单个列。Multi-value: Returns multiple rows and a single column.
  • 标量:返回单个行和单个列。Scalar: Returns a single row and a single column.

Azure Cosmos DB 中的 SQL 查询始终返回单个列(一个简单的值,或一个复杂文档)。SQL queries in Azure Cosmos DB always return a single column (either a simple value or a complex document). 因此,Azure Cosmos DB 中仅适用多值子查询和标量子查询。Therefore, only multi-value and scalar subqueries are applicable in Azure Cosmos DB. 只能在 FROM 子句中将多值子查询用作关系表达式。You can use a multi-value subquery only in the FROM clause as a relational expression. 可以在 SELECT 或 WHERE 子句中将标量子查询用作标量表达式,或者在 FROM 子句中用作关系表达式。You can use a scalar subquery as a scalar expression in the SELECT or WHERE clause, or as a relational expression in the FROM clause.

多值子查询Multi-value subqueries

多值子查询返回一组文档,始终在 FROM 子句中使用。Multi-value subqueries return a set of documents and are always used within the FROM clause. 它们用于:They're used for:

  • 优化 JOIN 表达式。Optimizing JOIN expressions.
  • 求值高开销的表达式一次,并多次引用。Evaluating expensive expressions once and referencing multiple times.

优化 JOIN 表达式Optimize JOIN expressions

多值子查询可以通过在 WHERE 子句中的每个 select-many 表达式后面(而不是所有 cross-join 后面)推送谓词,来优化 JOIN 表达式。Multi-value subqueries can optimize JOIN expressions by pushing predicates after each select-many expression rather than after all cross-joins in the WHERE clause.

请考虑下列查询:Consider the following query:

SELECT Count(1) AS Count
FROM c
JOIN t IN c.tags
JOIN n IN c.nutrients
JOIN s IN c.servings
WHERE t.name = 'infant formula' AND (n.nutritionValue > 0 
AND n.nutritionValue < 10) AND s.amount > 1

对于此查询,索引将匹配包含名为“infant formula”的标记的任一文档。For this query, the index will match any document that has a tag with the name "infant formula." 它是一个值为 0 到 10 的 nutrient 项,以及数量大于 1 的 serving 项。It's a nutrient item with a value between 0 and 10, and a serving item with an amount greater than 1. 此处的 JOIN 表达式将针对应用任何筛选器之前的每个匹配文档,执行所有 tags、nutrients 和 servings 数组项的叉积计算。The JOIN expression here will perform the cross-product of all items of tags, nutrients, and servings arrays for each matching document before any filter is applied.

然后,WHERE 子句将针对每个 <c, t, n, s> 元组应用筛选谓词。The WHERE clause will then apply the filter predicate on each <c, t, n, s> tuple. 例如,如果在匹配文档的三个数组中,每个数组包含 10 个项,则此子句将扩展为 1 x 10 x 10 x 10(即 1,000)个元组。For instance, if a matching document had 10 items in each of the three arrays, it will expand to 1 x 10 x 10 x 10 (that is, 1,000) tuples. 在与下一个表达式联接之前,使用此处的子查询可帮助筛选出联接的数组项。Using subqueries here can help in filtering out joined array items before joining with the next expression.

此查询等效于前面的查询,但使用了子查询:This query is equivalent to the preceding one but uses subqueries:

SELECT Count(1) AS Count
FROM c
JOIN (SELECT VALUE t FROM t IN c.tags WHERE t.name = 'infant formula')
JOIN (SELECT VALUE n FROM n IN c.nutrients WHERE n.nutritionValue > 0 AND n.nutritionValue < 10)
JOIN (SELECT VALUE s FROM s IN c.servings WHERE s.amount > 1)

假设 tags 数组中只有一个项与筛选器相匹配,而 nutrients 和 servings 数组各有 5 个项。Assume that only one item in the tags array matches the filter, and there are five items for both nutrients and servings arrays. 那么,JOIN 表达式将扩展为 1 x 1 x 5 x 5 = 25 个项,而不是第一个查询中的 1,000 个项。The JOIN expressions will then expand to 1 x 1 x 5 x 5 = 25 items, as opposed to 1,000 items in the first query.

求值一次,引用多次Evaluate once and reference many times

子查询可以帮助优化包含高开销表达式(例如,用户定义的函数 (UDF)、复杂字符串或算术表达式)的查询。Subqueries can help optimize queries with expensive expressions such as user-defined functions (UDFs), complex strings, or arithmetic expressions. 可以结合 JOIN 表达式使用子查询,以求值该表达式一次,但引用它多次。You can use a subquery along with a JOIN expression to evaluate the expression once but reference it many times.

以下查询执行 UDF GetMaxNutritionValue 两次:The following query runs the UDF GetMaxNutritionValue twice:

SELECT c.id, udf.GetMaxNutritionValue(c.nutrients) AS MaxNutritionValue
FROM c
WHERE udf.GetMaxNutritionValue(c.nutrients) > 100

下面是一个等效的查询,但它仅运行该 UDF 一次:Here's an equivalent query that runs the UDF only once:

SELECT TOP 1000 c.id, MaxNutritionValue
FROM c
JOIN (SELECT VALUE udf.GetMaxNutritionValue(c.nutrients)) MaxNutritionValue
WHERE MaxNutritionValue > 100

备注

请注意 JOIN 表达式的叉积行为。Keep in mind the cross-product behavior of JOIN expressions. 如果 UDF 表达式可能会求值为 undefined(未确定),则应该通过从子查询返回对象,而不是直接返回值,来确保 JOIN 表达式始终生成单个行。If the UDF expression can evaluate to undefined, you should ensure that the JOIN expression always produces a single row by returning an object from the subquery rather than the value directly.

下面是返回对象而不是返回值的类似示例:Here's a similar example that returns an object rather than a value:

SELECT TOP 1000 c.id, m.MaxNutritionValue
FROM c
JOIN (SELECT udf.GetMaxNutritionValue(c.nutrients) AS MaxNutritionValue) m
WHERE m.MaxNutritionValue > 100

此方法并不局限于 UDF,The approach is not limited to UDFs. 而是适用于任何可能存在较高开销的表达式。It applies to any potentially expensive expression. 例如,可以对数学函数 avg 采用相同的方法:For example, you can take the same approach with the mathematical function avg:

SELECT TOP 1000 c.id, AvgNutritionValue
FROM c
JOIN (SELECT VALUE avg(n.nutritionValue) FROM n IN c.nutrients) AvgNutritionValue
WHERE AvgNutritionValue > 80

模拟与外部引用数据的联接Mimic join with external reference data

你可能经常需要引用极少发生变化的静态数据,例如度量单位或国家/地区代码。You might often need to reference static data that rarely changes, such as units of measurement or country codes. 最好是不要复制每个文档的此类数据。It's better not to duplicate such data for each document. 避免这种复制可以节省存储空间,并通过保持较小的文档大小来提高写入性能。Avoiding this duplication will save on storage and improve write performance by keeping the document size smaller. 可以使用子查询通过引用数据的集合来模拟内部联接语义。You can use a subquery to mimic inner-join semantics with a collection of reference data.

例如,假设存在以下引用数据集:For instance, consider this set of reference data:

单位Unit 名称Name 乘数Multiplier 基础单位Base unit
ngng 纳克Nanogram 1.00E-091.00E-09 Gram
µgµg 微克Microgram 1.00E-061.00E-06 Gram
mgmg 毫克Milligram 1.00E-031.00E-03 Gram
gg Gram 1.00E+001.00E+00 Gram
kgkg 千克Kilogram 1.00E+031.00E+03 Gram
MgMg 兆克Megagram 1.00E+061.00E+06 Gram
GgGg 千兆克Gigagram 1.00E+091.00E+09 Gram
nJnJ 纳焦Nanojoule 1.00E-091.00E-09 焦耳Joule
µJµJ 微焦Microjoule 1.00E-061.00E-06 焦耳Joule
mJmJ 毫焦Millijoule 1.00E-031.00E-03 焦耳Joule
JJ 焦耳Joule 1.00E+001.00E+00 焦耳Joule
kJkJ 千焦Kilojoule 1.00E+031.00E+03 焦耳Joule
MJMJ 兆焦Megajoule 1.00E+061.00E+06 焦耳Joule
GJGJ 千兆焦Gigajoule 1.00E+091.00E+09 焦耳Joule
calcal 卡路里Calorie 1.00E+001.00E+00 卡路里calorie
kcalkcal 卡路里Calorie 1.00E+031.00E+03 卡路里calorie
IUIU 国际单位International units

以下查询模拟与此数据的联接,以便于将单位名称添加到输出:The following query mimics joining with this data so that you add the name of the unit to the output:

SELECT TOP 10 n.id, n.description, n.nutritionValue, n.units, r.name
FROM food
JOIN n IN food.nutrients
JOIN r IN (
    SELECT VALUE [
        {unit: 'ng', name: 'nanogram', multiplier: 0.000000001, baseUnit: 'gram'},
        {unit: 'µg', name: 'microgram', multiplier: 0.000001, baseUnit: 'gram'},
        {unit: 'mg', name: 'milligram', multiplier: 0.001, baseUnit: 'gram'},
        {unit: 'g', name: 'gram', multiplier: 1, baseUnit: 'gram'},
        {unit: 'kg', name: 'kilogram', multiplier: 1000, baseUnit: 'gram'},
        {unit: 'Mg', name: 'megagram', multiplier: 1000000, baseUnit: 'gram'},
        {unit: 'Gg', name: 'gigagram', multiplier: 1000000000, baseUnit: 'gram'},
        {unit: 'nJ', name: 'nanojoule', multiplier: 0.000000001, baseUnit: 'joule'},
        {unit: 'µJ', name: 'microjoule', multiplier: 0.000001, baseUnit: 'joule'},
        {unit: 'mJ', name: 'millijoule', multiplier: 0.001, baseUnit: 'joule'},
        {unit: 'J', name: 'joule', multiplier: 1, baseUnit: 'joule'},
        {unit: 'kJ', name: 'kilojoule', multiplier: 1000, baseUnit: 'joule'},
        {unit: 'MJ', name: 'megajoule', multiplier: 1000000, baseUnit: 'joule'},
        {unit: 'GJ', name: 'gigajoule', multiplier: 1000000000, baseUnit: 'joule'},
        {unit: 'cal', name: 'calorie', multiplier: 1, baseUnit: 'calorie'},
        {unit: 'kcal', name: 'Calorie', multiplier: 1000, baseUnit: 'calorie'},
        {unit: 'IU', name: 'International units'}
    ]
)
WHERE n.units = r.unit

标量子查询Scalar subqueries

标量子查询表达式是求值为单个值的子查询。A scalar subquery expression is a subquery that evaluates to a single value. 标量子查询表达式的值是该子查询的投影(SELECT 子句)值。The value of the scalar subquery expression is the value of the projection (SELECT clause) of the subquery. 可以在标量表达式有效的多个位置使用标量子查询表达式。You can use a scalar subquery expression in many places where a scalar expression is valid. 例如,可以在 SELECT 和 WHERE 子句中的任一表达式内使用标量子查询。For instance, you can use a scalar subquery in any expression in both the SELECT and WHERE clauses.

不过,使用标量子查询并不总是有助于优化。Using a scalar subquery doesn't always help optimize, though. 例如,将标量子查询作为参数传递给系统定义的或用户定义的函数并不能在资源单位 (RU) 消耗量与延迟方面带来好处。For example, passing a scalar subquery as an argument to either a system or user-defined functions provides no benefit in resource unit (RU) consumption or latency.

标量子查询可以进一步分类为:Scalar subqueries can be further classified as:

  • 简单表达式标量子查询Simple-expression scalar subqueries
  • 聚合标量子查询Aggregate scalar subqueries

简单表达式标量子查询Simple-expression scalar subqueries

简单表达式标量子查询属于相关子查询,其中的某个 SELECT 子句不包含任何聚合表达式。A simple-expression scalar subquery is a correlated subquery that has a SELECT clause that doesn't contain any aggregate expressions. 这些子查询不能提供优化方面的优势,因为编译器会将其转换为一个较大的简单表达式。These subqueries provide no optimization benefits because the compiler converts them into one larger simple expression. 内部与外部查询之间没有相关的上下文。There's no correlated context between the inner and outer queries.

以下是几个示例:Here are few examples:

示例 1Example 1

SELECT 1 AS a, 2 AS b

可以使用简单表达式标量子查询将此查询重写为:You can rewrite this query, by using a simple-expression scalar subquery, to:

SELECT (SELECT VALUE 1) AS a, (SELECT VALUE 2) AS b

这两个查询生成以下输出:Both queries produce this output:

[
  { "a": 1, "b": 2 }
]

示例 2Example 2

SELECT TOP 5 Concat('id_', f.id) AS id
FROM food f

可以使用简单表达式标量子查询将此查询重写为:You can rewrite this query, by using a simple-expression scalar subquery, to:

SELECT TOP 5 (SELECT VALUE Concat('id_', f.id)) AS id
FROM food f

查询输出:Query output:

[
  { "id": "id_03226" },
  { "id": "id_03227" },
  { "id": "id_03228" },
  { "id": "id_03229" },
  { "id": "id_03230" }
]

示例 3Example 3

SELECT TOP 5 f.id, Contains(f.description, 'fruit') = true ? f.description : undefined
FROM food f

可以使用简单表达式标量子查询将此查询重写为:You can rewrite this query, by using a simple-expression scalar subquery, to:

SELECT TOP 10 f.id, (SELECT f.description WHERE Contains(f.description, 'fruit')).description
FROM food f

查询输出:Query output:

[
  { "id": "03230" },
  { "id": "03238", "description":"Babyfood, dessert, tropical fruit, junior" },
  { "id": "03229" },
  { "id": "03226", "description":"Babyfood, dessert, fruit pudding, orange, strained" },
  { "id": "03227" }
]

聚合标量子查询Aggregate scalar subqueries

聚合标量子查询在其投影或筛选器中包含一个求值为单个值的聚合函数。An aggregate scalar subquery is a subquery that has an aggregate function in its projection or filter that evaluates to a single value.

示例 1:Example 1:

以下子查询在其投影中包含单个聚合函数表达式:Here's a subquery with a single aggregate function expression in its projection:

SELECT TOP 5 
    f.id, 
    (SELECT VALUE Count(1) FROM n IN f.nutrients WHERE n.units = 'mg'
) AS count_mg
FROM food f

查询输出:Query output:

[
  { "id": "03230", "count_mg": 13 },
  { "id": "03238", "count_mg": 14 },
  { "id": "03229", "count_mg": 13 },
  { "id": "03226", "count_mg": 15 },
  { "id": "03227", "count_mg": 19 }
]

示例 2Example 2

下面是包含多个聚合函数表达式的子查询:Here's a subquery with multiple aggregate function expressions:

SELECT TOP 5 f.id, (
    SELECT Count(1) AS count, Sum(n.nutritionValue) AS sum 
    FROM n IN f.nutrients 
    WHERE n.units = 'mg'
) AS unit_mg
FROM food f

查询输出:Query output:

[
  { "id": "03230","unit_mg": { "count": 13,"sum": 147.072 } },
  { "id": "03238","unit_mg": { "count": 14,"sum": 107.385 } },
  { "id": "03229","unit_mg": { "count": 13,"sum": 141.579 } },
  { "id": "03226","unit_mg": { "count": 15,"sum": 183.91399999999996 } },
  { "id": "03227","unit_mg": { "count": 19,"sum": 94.788999999999987 } }
]

示例 3Example 3

下面是在投影和筛选器中包含聚合子查询的查询:Here's a query with an aggregate subquery in both the projection and the filter:

SELECT TOP 5 
    f.id, 
    (SELECT VALUE Count(1) FROM n IN f.nutrients WHERE n.units = 'mg') AS count_mg
FROM food f
WHERE (SELECT VALUE Count(1) FROM n IN f.nutrients WHERE n.units = 'mg') > 20

查询输出:Query output:

[
  { "id": "03235", "count_mg": 27 },
  { "id": "03246", "count_mg": 21 },
  { "id": "03267", "count_mg": 21 },
  { "id": "03269", "count_mg": 21 },
  { "id": "03274", "count_mg": 21 }
]

编写此查询的更好方法是在子查询中进行联接,并在 SELECT 和 WHERE 子句中引用子查询别名。A more optimal way to write this query is to join on the subquery and reference the subquery alias in both the SELECT and WHERE clauses. 此查询更有效,因为你只需执行 join 语句中的子查询,而无需同时执行投影和筛选器中的子查询。This query is more efficient because you need to execute the subquery only within the join statement, and not in both the projection and filter.

SELECT TOP 5 f.id, count_mg
FROM food f
JOIN (SELECT VALUE Count(1) FROM n IN f.nutrients WHERE n.units = 'mg') AS count_mg
WHERE count_mg > 20

EXISTS 表达式EXISTS expression

Azure Cosmos DB 支持 EXISTS 表达式。Azure Cosmos DB supports EXISTS expressions. 这是 Azure Cosmos DB SQL API 中内置的聚合标量子查询。This is an aggregate scalar subquery built into the Azure Cosmos DB SQL API. EXISTS 是一个布尔表达式,它采用某个子查询表达式,如果该子查询返回任何行,则 EXISTS 返回 true。EXISTS is a Boolean expression that takes a subquery expression and returns true if the subquery returns any rows. 否则返回 false。Otherwise, it returns false.

由于 Azure Cosmos DB SQL API 不区分布尔表达式和其他任何标量表达式,因此,可以同时在 SELECT 和 WHERE 子句中使用 EXISTS。Because the Azure Cosmos DB SQL API doesn't differentiate between Boolean expressions and any other scalar expressions, you can use EXISTS in both SELECT and WHERE clauses. T-SQL 则与此不同,其中的布尔表达式(例如 EXISTS、BETWEEN 和 IN)限制为筛选器。This is unlike T-SQL, where a Boolean expression (for example, EXISTS, BETWEEN, and IN) is restricted to the filter.

如果 EXISTS 子查询返回未定义的单个值,则 EXISTS 将求值为 false。If the EXISTS subquery returns a single value that's undefined, EXISTS will evaluate to false. 例如,假设以下查询求值为 false:For instance, consider the following query that evaluates to false:

SELECT EXISTS (SELECT VALUE undefined)

如果省略上述子查询中的 VALUE 关键字,则该查询将求值为 true:If the VALUE keyword in the preceding subquery is omitted, the query will evaluate to true:

SELECT EXISTS (SELECT undefined) 

该子查询在对象中的选定列表内括住值列表。The subquery will enclose the list of values in the selected list in an object. 如果选定的列表不包含任何值,该子查询将返回单个值 '{}'。If the selected list has no values, the subquery will return the single value '{}'. 此值已定义,因此 EXISTS 求值为 true。This value is defined, so EXISTS evaluates to true.

示例:将 ARRAY_CONTAINS 和 JOIN 重写为 EXISTSExample: Rewriting ARRAY_CONTAINS and JOIN as EXISTS

ARRAY_CONTAINS 的一个常见用例是根据某个项在数组中的存在性筛选某个文档。A common use case of ARRAY_CONTAINS is to filter a document by the existence of an item in an array. 在本例中,我们将检查 tags 数组是否包含名为“orange”的项。In this case, we're checking to see if the tags array contains an item named "orange."

SELECT TOP 5 f.id, f.tags
FROM food f
WHERE ARRAY_CONTAINS(f.tags, {name: 'orange'})

可将上述查询重写为使用 EXISTS:You can rewrite the same query to use EXISTS:

SELECT TOP 5 f.id, f.tags
FROM food f
WHERE EXISTS(SELECT VALUE t FROM t IN f.tags WHERE t.name = 'orange')

此外,ARRAY_CONTAINS 只能检查某个值是否等于数组中的任何元素。Additionally, ARRAY_CONTAINS can only check if a value is equal to any element within an array. 如果需要在数组属性中包含更复杂的筛选器,请使用 JOIN。If you need more complex filters on array properties, use JOIN.

假设以下查询根据数组中的 units 和 nutritionValue 属性进行筛选:Consider the following query that filters based on the units and nutritionValue properties in the array:

SELECT VALUE c.description
FROM c
JOIN n IN c.nutrients
WHERE n.units= "mg" AND n.nutritionValue > 0

对于集合中的每个文档,将使用其数组元素执行叉积计算。For each of the documents in the collection, a cross-product is performed with its array elements. 使用此 JOIN 操作可以根据数组中的属性进行筛选。This JOIN operation makes it possible to filter on properties within the array. 但是,此查询的 RU 消耗量非常大。However, this query's RU consumption will be significant. 例如,如果 1,000 个文档包含每个数组中的 100 个项,则它会扩展为 1,000 x 100(即 100,000)个元组。For instance, if 1,000 documents had 100 items in each array, it will expand to 1,000 x 100 (that is, 100,000) tuples.

使用 EXISTS 可以帮助避免这种高开销的叉积计算:Using EXISTS can help to avoid this expensive cross-product:

SELECT VALUE c.description
FROM c
WHERE EXISTS(
    SELECT VALUE n
    FROM n IN c.nutrients
    WHERE n.units = "mg" AND n.nutritionValue > 0
)

在本例中,你将根据 EXISTS 子查询中的数组元素进行筛选。In this case, you filter on array elements within the EXISTS subquery. 如果某个数组元素与筛选器匹配,则你需要投影该元素,而 EXISTS 将求值为 true。If an array element matches the filter, then you project it and EXISTS evaluates to true.

还可以指定 EXISTS 的别名,并在投影中引用它:You can also alias EXISTS and reference it in the projection:

SELECT TOP 1 c.description, EXISTS(
    SELECT VALUE n
    FROM n IN c.nutrients
    WHERE n.units = "mg" AND n.nutritionValue > 0) as a
FROM c

查询输出:Query output:

[
    {
        "description": "Babyfood, dessert, fruit pudding, orange, strained",
        "a": true
    }
]

ARRAY 表达式ARRAY expression

可以使用 ARRAY 表达式将查询结果投影为数组。You can use the ARRAY expression to project the results of a query as an array. 只能在查询的 SELECT 子句中使用此表达式。You can use this expression only within the SELECT clause of the query.

SELECT TOP 1   f.id, ARRAY(SELECT VALUE t.name FROM t in f.tags) AS tagNames
FROM  food f

查询输出:Query output:

[
    {
        "id": "03238",
        "tagNames": [
            "babyfood",
            "dessert",
            "tropical fruit",
            "junior"
        ]
    }
]

与使用其他子查询时一样,可以使用包含 ARRAY 表达式的筛选器。As with other subqueries, filters with the ARRAY expression are possible.

SELECT TOP 1 c.id, ARRAY(SELECT VALUE t FROM t in c.tags WHERE t.name != 'infant formula') AS tagNames
FROM c

查询输出:Query output:

[
    {
        "id": "03226",
        "tagNames": [
            {
                "name": "babyfood"
            },
            {
                "name": "dessert"
            },
            {
                "name": "fruit pudding"
            },
            {
                "name": "orange"
            },
            {
                "name": "strained"
            }
        ]
    }
]

Array 表达式还可以跟在子查询中的 FROM 子句后面。Array expressions can also come after the FROM clause in subqueries.

SELECT TOP 1 c.id, ARRAY(SELECT VALUE t.name FROM t in c.tags) as tagNames
FROM c
JOIN n IN (SELECT VALUE ARRAY(SELECT t FROM t in c.tags WHERE t.name != 'infant formula'))

查询输出:Query output:

[
    {
        "id": "03238",
        "tagNames": [
            "babyfood",
            "dessert",
            "tropical fruit",
            "junior"
        ]
    }
]

后续步骤Next steps