gpt4 book ai didi

循环结构的 Elasticsearch 映射

转载 作者:行者123 更新时间:2023-12-03 00:01:39 25 4
gpt4 key购买 nike

我正在尝试对 JSON 数据进行一些映射,如下所示

    "0": {
"ip": "147.135.210.114",
"countryName": "United States",
"countryCode": "US",
"frequency": "46",
"updown": -0.25579565572885,
"viewCount": "28"
},
"1": {
"ip": "171.255.199.129",
"danger": "94.42262",
"countryName": "Viet Nam",
"countryCode": "VN",
"frequency": "40",
"updown": -0.088216630501414,
"viewCount": null
},
"2": {
"ip": "52.163.62.13",
"danger": "94.18168",
"countryName": "United States",
"countryCode": "US",
"frequency": "46",
"updown": -0.016932485456378,
"viewCount": "5"
},
"3": {
"ip": "151.80.140.233",
"danger": "93.77446",
"countryName": "Unknown",
"countryCode": "Unknown",
"frequency": "46",
"updown": -0.31354507272874,
"viewCount": "10"
},

如您所见,有很多对象(我什至不确定它是否称为对象)。
该对象具有不同的名称(0,1,2,3,4...)和相同的元素(ip,danger ...)。

如何一次映射具有不同名称的元素?有可能吗?

提前感谢:-)

最佳答案

您可以使用相同的映射来映射具有不同名称的元素,但这不太可能有用(取决于您的用例)。

主要有两种选择:

  • 使用 dynamic_templates描述具有重复结构的数据;
  • reshape 数据并使用 nested数据类型
  • dynamic_templates
    优点:
  • 做这项工作
  • 无需更改数据

  • 缺点:
  • 更难或不可能查询
  • map 爆炸的风险

  • reshape + nested
    优点:
  • 做这项工作
  • 查询能力无限制

  • 缺点:
  • 必须更改数据格式

  • 下面来详细介绍。

    使用带有 dynamic_templates 的动态映射

    一般情况下,使用 dynamic mapping允许您添加任意结构的对象,其类型将根据 some predefined rules 动态猜测.

    动态映射使您对数据结构的控制更少,并可能导致 mapping explosion .

    如果您对动态映射很满意,并且只想调整它的应用方式,您可以使用 dynamic_templates .

    您必须在插入任何数据之前创建一个映射,可能如下所示:
    PUT dyno
    {
    "mappings": {
    "dyno": {
    "dynamic_templates": [
    {
    "dynoField": {
    "path_match": "myPath.*",
    "mapping": {
    "properties": {
    "ip": {
    "type": "keyword"
    },
    "danger": {
    "type": "float"
    },
    "countryName": {
    "type": "keyword"
    },
    "countryCode": {
    "type": "keyword"
    },
    "frequency": {
    "type": "integer"
    },
    "updown": {
    "type": "float"
    },
    "viewCount": {
    "type": "integer"
    }
    }
    }
    }
    }
    ],
    "properties": {
    "myPath": {
    "type": "object"
    }
    }
    }
    }
    }

    这里 dynamic_templates部分应用于 myPath 的所有键对象(0,1,2,3,4 等)。

    索引第一个文档后,您从 ES 获得的映射实际上如下所示:
    {
    "dyno": {
    "aliases": {},
    "mappings": {
    "dyno": {
    "dynamic_templates": [
    ...
    ],
    "properties": {
    "myPath": {
    "properties": {
    "0": {
    "properties": {
    "countryCode": {
    "type": "keyword"
    },
    "countryName": {
    "type": "keyword"
    },
    "danger": {
    "type": "float"
    },
    "frequency": {
    "type": "integer"
    },
    "ip": {
    "type": "keyword"
    },
    "updown": {
    "type": "float"
    },
    "viewCount": {
    "type": "integer"
    }
    }
    },
    "1": {
    "properties": {
    "countryCode": {
    "type": "keyword"
    }, ...
    },
    "2": {
    "properties": {
    "countryCode": {
    "type": "keyword"
    }, ...
    },
    "3": {
    "properties": {
    "countryCode": {
    "type": "keyword"
    }, ...
    }
    }
    }
    }
    }
    }
    }
    }
    }

    请注意,对于对象的每个不同“名称”,ES 创建了一个单独的映射部分。

    尽管这完全符合您的要求,但它可能没有用。如果您有一个用例,您想选择具有特定 countryCode 的所有文档您可能会构建这样的查询:
    POST dyno/dyno/_search
    {
    "query": {
    "match": {
    "myPath.1.countryCode": "VN"
    }
    }
    }

    但这只会返回与“名称” 1 的对象匹配。 .如果“名称”的集合很大和/或事先不知道,那么查询它们将非常复杂。

    reshape 数据并使用 nested类型

    能够搜索任何对象的 countryCode您可能希望通过以下方式 reshape 数据:
    {
    "myPath": [
    {
    "__name": "0",
    "ip": "147.135.210.114",
    "countryName": "United States",
    "countryCode": "US",
    "frequency": "46",
    "updown": -0.25579565572885,
    "viewCount": "28"
    },
    {
    "__name": "1",
    "ip": "171.255.199.129",
    "danger": "94.42262",
    "countryName": "Viet Nam",
    "countryCode": "VN",
    "frequency": "40",
    "updown": -0.088216630501414,
    "viewCount": null
    }, ...
    ]
    }

    棘手的部分是,为了能够搜索 myPath 的项目单独列出,必须使用 nested 数据类型。

    在这种情况下,您的映射可以是 dynamicstrict ,最适合你的。 dynamic 中的映射案例可能看起来像这样简单:
    PUT dyno
    {
    "mappings": {
    "dyno": {
    "properties": {
    "myPath": {
    "type": "nested"
    }
    }
    }
    }
    }

    这将允许您执行如下查询:
    POST dyno/dyno/_search
    {
    "query": {
    "nested": {
    "path": "myPath",
    "query": {
    "match": {
    "myPath.countryCode.keyword": "VN"
    }
    }
    }
    }
    }

    请注意,为了查询 nested您必须使用的字段 nested query .一个不错的起点 nested数据类型为 this chapter的指南。

    关于嵌套字段的最后说明

    事实上,对于 nested field ES 为列表中的每个项目索引一个隐式文档,因此索引和搜索这种类型的对象比非嵌套对象慢。

    您可以考虑将这些具有不同“名称”的对象拆分为单独的 ES 文档。

    希望有帮助!

    关于循环结构的 Elasticsearch 映射,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48553581/

    25 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com