检查一个整数范围的字典键

Checking for a dictionary key which is a range of integers

我正在构建制造商词典。它看起来像这样:

mfgs =     {17491: 'DS', 6543: 'AC'}

在这种情况下,我需要表示一个整数范围,这些整数都指的是同一个制造商。 (例如1 - 99都是DC生产的)

我看到您可以创建表示范围的字典键。

mfgs =     {17491: 'DS', 6543: 'AC', (1,99): 'DC'}

稍后,我将从外部文件中获取一个整数。根据遇到的值,我会将相应的制造商记录到另一个文件中。

我不清楚如何检查是否存在有效的 key/value 对(无论是数字还是数字范围)并记录 "Unknown" 如果没有构建扩展 if/then 说明字典中定义的键。

好像try/except是合适的,但是如果遇到21,mfg[21]就失败了,应该不会。

您需要的不仅仅是简单的哈希图(即字典)查找。哈希图查找特定的键,而不是某个键是否在任何现有键的范围内。

你有两个简单的选择。

  1. 如果您提前知道范围,请在查找之前将整数转换为范围:

    def range_from_id(manufacturer_id):
        if 1 <= manufacturer_id <= 99:
            return (1, 99)
        return manufacturer_id
    
    manufacturer_id = ... from file ...
    manufacturer_range = range_from_id(manufacturer_id)
    manufacturer = mfgs.get(manufacturer_range, "Unknown")
    
  2. 如果不这样做,则在单独的字典中跟踪范围,并遍历所有可能的值:

    mfgs = {17491: 'DS', ...}
    mfg_ranges = {(1, 99): 'DC', ...}
    
    def lookup_manufacturer(manufacturer_id):
        # direct look-up:
        if manufacturer_id in mfgs: 
            return mfgs[manufacturer_id]
    
        # range look-up:
        for (start, end), mfg in mfg_ranges.items():
            if start <= manufacturer_id <= end:
                return mfg
    
        return "Unknown"
    

    如果速度很重要,请注意此选项将采用 O(n),其中 n 是您拥有的范围数。更合适的方法是使用二叉树,如 amit answered here. This would require using a 3rd party library like bintrees

我找到了一种方法来做到这一点。请注意,我在那里是因为我们在一个 for 循环中迭代找到的项目。 mfgs 是一个预填充的字典。

try:
    drivers_list[i]['mfg'] = mfgs[mfg] # Attempt to store in dictionary
except:
    if 1 <= mfg <= 31:   # On exception, see if it's the known mfg.
        drivers_list[i]['mfg'] = 'The known manufacturer'  # Between 1 and 31
    else:
        drivers_list[i]['mfg'] = 'Unknown' # otherwise post unknown