доступ к значениям словаря с помощью дубликатов ключей

#python #dictionary

#python #словарь

Вопрос:

У меня есть словарь, который выглядит следующим образом:

 reply = {icon:[{name:whatever,url:logo1.png},{name:whatever,url:logo2.png}]}
  

как мне получить доступ к logo1.png?

Я пытался :

 print reply[icon][url]
  

и это выдает мне ошибку:

 list indices must be integers, not str
  

EDIT:

Имейте в виду, что иногда мой словарь меняется на это :

 reply = {icon:{name:whatever,url:logo1.png}}
  

Мне нужно общее решение, которое будет работать для обоих типов словарей

EDIT2: мое решение было таким :

     try:
        icon = reply['icon']['url']
        print icon
    except Exception:
        icon = reply['icon'][0]['url']
        print ipshit,icon
  

Это работает, но выглядит ужасно. Мне было интересно, есть ли более простой способ, чем этот

Комментарии:

1. Для обоих нет простого решения, потому что у одного есть словари в качестве значений, а у другого есть списки. Вам нужно будет явно проверить, является ли значение списком или dict . Лучше, чтобы значения всегда были списками, даже если только список с одним элементом.

2. Кроме того, это должно перейти в класс, чтобы вы могли создавать правильные объекты и получать к ним доступ icon.url .

3. Почему «иногда мой словарь меняется на это»? Почему бы просто не иметь список значений в обоих случаях? Этот формат находится вне вашего контроля?

4. @user2357112 да, формат находится вне моего контроля .. это ответ с веб-сайта.. который изменяется на два типа упомянутых словарей

Ответ №1:

Вы пробовали это?

 reply[icon][0][url]
  

Если вы точно знаете все различные типы ответов, которые вы получите, вам придется написать синтаксический анализатор, в котором вы явно проверяете, являются ли значения списками или dicts.

Вы могли бы попробовать это, если вы описали только две возможности:

 def get_icon_url(reply):
    return reply['icon'][0]['url']
    if type(reply['icon']) is list else reply['icon']['url']
  

Комментарии:

1. это работает для словарей первого типа, но не работает для словарей второго типа (см. Редактирование)

Ответ №2:

итак, в этом случае icon является ключом к списку, в котором есть два словаря с двумя парами ключ / значение в каждом. Кроме того, похоже, что вы можете захотеть, чтобы ваши ключи были строками (icon = ‘icon’, name =’name’).. но, возможно, они являются переменными, и в этом случае игнорируйте, я собираюсь использовать строки ниже, потому что это кажется наиболее правильным

итак:

 reply['icon'] # is equal to a list: []
reply['icon'][0] # is equal to a dictionary: {}
reply['icon'][0]['name'] # is equal to 'whatever'
reply['icon'][0]['url'] # is equal to 'logo1.png'
reply['icon'][1] # is equal to the second dictionary: {}
reply['icon'][1]['name'] # is equal to 'whatever'
reply['icon'][1]['url'] # is equal to 'logo2.png'
  

вы можете получить доступ к элементам этих внутренних словарей, либо зная, сколько элементов в списке, и явно ссылаясь на тему, как сделано выше, или вы можете перебирать их:

 for picture_dict in reply['icon']:
    name = picture_dict['name'] # is equal to 'whatever' on both iterations
    url = picture_dict['url'] #is 'logo1.png' on first iteration, 'logo2.png' on second.
  

Приветствия!

Ответ №3:

Не так уж и отличается, но, возможно, это выглядит лучше (KeyError дает более точный контроль):

 icon_data = reply['icon']
try:
    icon = icon_data['url']
    print icon
except KeyError:
    icon = icon_data[0]['url']
    print ipshit,icon
  

или:

 icon_data = reply['icon']
if isinstance(icon_data, list):
    icon_data = icon_data[0]
icon = icon_data['url']