Механизм правил на основе иерархического соответствия - PullRequest
0 голосов
/ 23 февраля 2020

Скажем, у меня есть набор данных (городов) с этой структурой:

  • ID
  • Город
  • Штат
  • Страна
  • Континент

И у меня есть таблица конфигурации (ключ, значение), где ключ может быть комбинацией вышеуказанных параметров

Например:

{
    "continent": "asia"
}

или

{
    "continent": "asia",
    "country" : "india"
}

или

{
    "continent": "asia",
    "country" : "india",
    "state" : "maharashtra",
    "city" : "mumbai"
}

Теперь я хочу сделать самое близкое совпадение городов из 1-го набора данных с записями в конфигурации.

Для Например, если у меня есть

city: mumbai, state: maharashtra, country: india, continent: asia

, оно должно совпадать, 3-я запись в приведенной выше конфигурации.

Если у меня

city: tokyo, state: Kantō, country: japan, continent: asia

, оно должно совпадать с 1-й записью в Конфигурация выше.

Я ищу предложения, если что-то легко доступно для такого сценария.

Я открыт для хранения конфигураций другим способом, если таковые имеются.

В идеале я хотел бы получить решение, в котором я могу передать несколько записей (входов), и оно должно возвращать наиболее близкие совпадающие конфигурации для каждого из входов.

Ответы [ 2 ]

1 голос
/ 23 февраля 2020

С риском, что я неправильно пойму вопрос, я бы:

  • собрал записи конфигурации в древовидной структуре данных, для более быстрого поиска
  • нашел бы соответствие для одного ввод данных за раз, проходя через это дерево

Вот как это будет выглядеть:

class Config:
    def __init__(self):
        self.continents = {}

    def add(self, config):
        collection = self.continents
        for prop in ["continent", "country", "state", "city"]:
            if prop not in config:
                break
            key = config[prop]
            if key not in collection:
                collection[key] = {}
            collection = collection[key]
        collection["config"] = config

    def get(self, data):
        collection = self.continents
        config = None
        for prop in ["continent", "country", "state", "city"]:
            if prop not in data or data[prop] not in collection:
                break
            collection = collection[data[prop]]
            if "config" in collection:
                config = collection["config"]
        return config

Вышеприведенный класс можно использовать следующим образом.

Сначала создайте экземпляр и заполните его записями конфигурации:

config = Config()

config.add({ "continent": "asia"})
config.add({ "continent": "asia", "country": "india" })
config.add({ "continent": "asia", "country": "india", 
             "state": "maharashtra", "city": "mumbai" })

Затем выполните итерацию ваших записей данных и для каждого вызова config.get, чтобы получить наиболее подходящую конфигурацию. Например:

print(config.get({ "city": "mumbai", "state": "maharashtra", 
                   "country": "india", "continent": "asia"}))

print(config.get({"city": "tokyo", "state": "kantō", 
                   "country": "japan", "continent": "asia"}))
0 голосов
/ 23 февраля 2020

Здесь будет полезен OrderedDict, чтобы вы могли сохранить иерархию города> штата> страны> континента.

from collections import OrderedDict

config = OrderedDict({"city" : "mumbai",
                      "state" : "maharashtra",
                      "country" : "india",
                      "continent": "asia"})

def get_closest_match(**kwargs):
    for key in config.keys():
        if kwargs[key] == config[key]:
            return f'{key}: {config[key]}'


>>> get_closest_match(city='mumbai', state='maharashtra', country='india', continent='asia')
'city: mumbai'
>>> get_closest_match(city='tokyo', state='Kantō', country='japan', continent='asia')
'continent: asia'
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...