MySQL高级数据类型之:`MySQL`的`JSON`路径:`$`、`[*]`、`[#]`和`.key`的深入理解。

MySQL JSON 路径深入理解:$[*][#].key

大家好,今天我们深入探讨 MySQL JSON 数据类型中的路径表达式。JSON 路径是查询和操作 JSON 文档的关键,理解这些路径表达式对于有效地使用 MySQL JSON 功能至关重要。我们将重点讲解 $[*][#].key 这四个核心元素,并通过实例演示它们的应用场景。

JSON 数据类型基础回顾

在深入 JSON 路径之前,我们先简单回顾一下 MySQL 中的 JSON 数据类型。JSON 数据类型允许我们在数据库中存储和查询 JSON 格式的数据。这意味着我们可以存储复杂的数据结构,如对象和数组,而无需将它们分解成多个关系型表。

创建包含 JSON 列的表:

CREATE TABLE products (
    id INT PRIMARY KEY AUTO_INCREMENT,
    product_name VARCHAR(255),
    details JSON
);

插入 JSON 数据:

INSERT INTO products (product_name, details) VALUES
('Laptop', '{"brand": "Dell", "model": "XPS 13", "specs": {"cpu": "Intel i7", "ram": "16GB", "storage": "512GB SSD"}}'),
('Smartphone', '{"brand": "Samsung", "model": "Galaxy S23", "specs": {"screen": "6.1 inch", "camera": "50MP", "storage": "256GB"}}'),
('Tablet', '{"brand": "Apple", "model": "iPad Pro", "specs": {"screen": "12.9 inch", "processor": "M2", "storage": "512GB"}}'),
('Headphones', '{"brand": "Sony", "model": "WH-1000XM5", "features": ["Noise Cancelling", "Bluetooth", "Hi-Res Audio"]}');

INSERT INTO products (product_name, details) VALUES
('Book', '[{"title": "The Lord of the Rings", "author": "J.R.R. Tolkien"}, {"title": "Pride and Prejudice", "author": "Jane Austen"}]');

现在我们有了包含 JSON 数据的 products 表,可以开始学习如何使用 JSON 路径来访问和操作这些数据。

$:根对象

$ 符号表示 JSON 文档的根对象。它是所有 JSON 路径的起点。

示例:检索整个 JSON 文档

SELECT details FROM products WHERE product_name = 'Laptop';

这个查询会返回 Laptop 产品的整个 details JSON 文档。

现在,我们使用 JSON 路径来提取特定的信息。

SELECT JSON_EXTRACT(details, '$') FROM products WHERE product_name = 'Laptop';

虽然这个查询的结果和上一个查询相同,但它更清楚地表明我们正在使用 JSON 路径来访问根对象。JSON_EXTRACT() 函数是 MySQL 中用于从 JSON 文档中提取数据的关键函数。 $ 通常和其他路径表达式结合使用,单独使用的意义不大。

.key:访问 JSON 对象中的键值

.key 用于访问 JSON 对象中的特定键的值。它允许我们深入到 JSON 对象的层次结构中。

示例:检索 brand 属性

SELECT JSON_EXTRACT(details, '$.brand') FROM products WHERE product_name = 'Laptop';

这个查询会返回 Laptop 产品的 brand 属性的值,即 Dell

示例:检索嵌套的 cpu 属性

SELECT JSON_EXTRACT(details, '$.specs.cpu') FROM products WHERE product_name = 'Laptop';

这个查询会返回 Laptop 产品 specs 对象中的 cpu 属性的值,即 Intel i7

.key 可以链式使用,以访问嵌套在多层 JSON 对象中的属性。

使用 ->> 运算符简化语法

MySQL 提供了一个更简洁的语法来提取 JSON 属性,即 ->> 运算符。它等价于 JSON_EXTRACT() 函数,但会自动将结果转换为字符串。

SELECT details->>'$.brand' FROM products WHERE product_name = 'Laptop';
SELECT details->>'$.specs.cpu' FROM products WHERE product_name = 'Laptop';

这两个查询与使用 JSON_EXTRACT() 的查询返回相同的结果,但语法更简洁。

[*]:访问 JSON 数组中的所有元素

[*] 用于访问 JSON 数组中的所有元素。它允许我们迭代数组中的每个元素,并对它们执行操作。

示例:如果 details 列包含一个 JSON 数组,如何访问所有元素

假设 details 列包含一个如下所示的 JSON 数组:

[
  {"title": "The Lord of the Rings", "author": "J.R.R. Tolkien"},
  {"title": "Pride and Prejudice", "author": "Jane Austen"}
]

我们可以使用 [*] 来访问数组中的所有元素。

SELECT JSON_EXTRACT(details, '$[*].title') FROM products WHERE product_name = 'Book';

这个查询会返回一个包含所有书籍标题的 JSON 数组:["The Lord of the Rings", "Pride and Prejudice"]

*示例:结合 .key 和 `[]`**

我们可以结合 .key[*] 来访问数组中每个元素的特定属性。

SELECT details->>'$[*].author' FROM products WHERE product_name = 'Book';

这个查询会返回一个包含所有书籍作者的 JSON 数组:["J.R.R. Tolkien", "Jane Austen"]

使用 JSON_TABLE() 函数处理 JSON 数组

虽然 [*] 可以提取数组中的元素,但它返回的是一个 JSON 数组。如果我们需要将数组中的每个元素作为单独的行进行处理,可以使用 JSON_TABLE() 函数。

SELECT jt.title, jt.author
FROM products
JOIN JSON_TABLE(details, '$[*]' COLUMNS (
    title VARCHAR(255) PATH '$.title',
    author VARCHAR(255) PATH '$.author'
)) AS jt
WHERE product_name = 'Book';

这个查询会将 JSON 数组展开成一个虚拟表 jt,其中每一行代表数组中的一个元素。然后,我们可以像查询普通表一样查询这个虚拟表。

title author
The Lord of the Rings J.R.R. Tolkien
Pride and Prejudice Jane Austen

[#]:数组的长度

[#] 用于获取 JSON 数组的长度。它返回数组中元素的数量。

示例:获取数组的长度

SELECT JSON_LENGTH(details) FROM products WHERE product_name = 'Book';

或者也可以这样写:

SELECT JSON_EXTRACT(details, '$[#]') FROM products WHERE product_name = 'Book';

这两个查询都会返回 2,因为 details 列包含一个包含两个元素的 JSON 数组。

[#] 的注意事项

  • [#] 只能用于 JSON 数组。如果用于 JSON 对象,它会返回 NULL
  • JSON_LENGTH() 函数是获取 JSON 数组长度的更通用的方法,因为它也可以用于计算 JSON 对象中键的数量。

综合示例:复杂的 JSON 查询

让我们看一个更复杂的示例,演示如何结合使用 $.key[*][#] 来执行更高级的 JSON 查询。

假设我们想要找到所有具有 "Noise Cancelling" 功能的耳机。details 列的示例如下:

{"brand": "Sony", "model": "WH-1000XM5", "features": ["Noise Cancelling", "Bluetooth", "Hi-Res Audio"]}

我们可以使用以下查询来实现:

SELECT product_name
FROM products
WHERE JSON_CONTAINS(details->>'$.features', '"Noise Cancelling"');

JSON_CONTAINS() 函数检查 JSON 数组中是否包含指定的字符串。 或者,我们可以使用 JSON_SEARCH() 函数:

SELECT product_name
FROM products
WHERE JSON_SEARCH(details, 'one', 'Noise Cancelling') IS NOT NULL;

JSON_SEARCH() 函数在 JSON 文档中搜索指定的字符串。如果找到该字符串,则返回该字符串的路径;否则,返回 NULL

总结:掌握 JSON 路径是关键

理解 $.key[*][#] 是掌握 MySQL JSON 数据类型的关键。这些路径表达式允许我们有效地访问和操作 JSON 文档中的数据。通过结合使用这些元素,我们可以执行复杂的 JSON 查询,并从 JSON 数据中提取有用的信息。

JSON 路径的灵活应用

掌握 JSON 路径后,就能灵活的从JSON数据中提取、过滤和更新数据,实现更复杂的数据处理需求。

持续实践才能熟练掌握

JSON 路径的学习需要不断实践,多尝试不同的查询和操作,才能真正理解其工作原理和应用场景。

更多高级技巧等你探索

MySQL JSON 数据类型还有很多高级特性等待我们去探索,例如 JSON 值的更新、JSON 值的合并等等,继续学习,精益求精。

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注