Распаковать список элементов в фрейм данных pandas

#python #pandas

#python #pandas

Вопрос:

Я пытаюсь создать фрейм данных pandas на основе некоторых ответов, полученных от API. Я могу получить доступ к элементам, которые не являются вложенными, но не могут получить доступ к вложенным элементам.

Это часть ответа, который я получил.

     [{'account_currency': 'USD',
  'account_name': 'S series',
  'actions': [{'action_type': 'video_view', 'value': '1500'},
              {'action_type': 'post_reaction', 'value': '39'}],
  'video_p100_watched_actions': [{'action_type': 'video_view',
                                  'value': '200'}]},
 {'account_currency': 'USD',
  'account_name': 'S New series',
  'actions': [{'action_type': 'video_view', 'value': '1400'},
              {'action_type': 'post_reaction', 'value': '17'}],
  'video_p100_watched_actions': [{'action_type': 'video_view',
                                  'value': '1200'}]}]
  

Мой подход:

 final_results = []
for obj in results:
    video_100 = obj['video_p100_watched_actions']
    actions = obj['actions']
    final_results.append([obj['account_name'], obj['account_currency']])
  

Я пытаюсь добавить post_reaction в final_result, но не могу получить доступ к элементу.

Ожидаемый результат:

 Currency    Account name    Post Reaction   video view
USD         Series          39              200
USD         New Series      17              1200
  

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

1. @jezrael это список

2. Я получил SyntaxError: invalid syntax образец данных

3. @jezrael Я только что отредактировал ответ. не хватало одной скобки.

4. Все еще ошибка 'video_p100_watched_actions': [{'action_type': 'video_view', 'value': '1300'}], ^ SyntaxError: invalid syntax

5. @jezrael две фигурные скобки, присутствующие перед ‘account_currency’: ‘GBP’, отсутствуют.

Ответ №1:

Используйте json_normalize с concat , преобразуйте value в целое число и поворачивайте с помощью DataFrame.pivot_table :

 df1 = pd.json_normalize(results, 'actions', ['account_currency','account_name'])
df1 = df1[df1['action_type'].ne('video_view')]

df2 = pd.json_normalize(results, 'video_p100_watched_actions',
          ['account_currency','account_name'])

df = (pd.concat([df1, df2], ignore_index=True)
        .assign(value = lambda x: x['value'].astype(int))
        .pivot_table(index=['account_currency','account_name'], 
                     columns='action_type', 
                     values='value', 
                     aggfunc='sum')
        .reset_index())
print (df)
action_type account_currency  account_name  post_reaction  video_view
0                        USD  S New series             17        1200
1                        USD      S series             39         200
    
  

Ваше решение должно быть изменено:

 final_results = []
for obj in results:
    video_100 = dict([(x['action_type'], x['value']) 
                     for x in obj['video_p100_watched_actions']])
    actions = dict([(x['action_type'], x['value']) 
                    for x in obj['actions'] if x['action_type'] == 'post_reaction'])
    d={**{k:v for k,v in obj.items() if k not in ['actions','video_p100_watched_actions']},
         **video_100, **actions}
    final_results.append(d)

df = pd.DataFrame(final_results)
print (df)
  account_currency  account_name video_view post_reaction
0              USD      S series        200            39
1              USD  S New series       1200            17
  

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

1. @MishD — Ок, удалены строки с video_view помощью for df1 , теперь выходные данные совпадают.

Ответ №2:

Этот код должен вывести значение post_reaction:

 final_results = []
for obj in results:
    post_reaction = obj['actions'][1]['value']
    final_results.append(post_reaction)

print(final_results)
  

В строке post_reaction = obj['actions'][1]['value'] часть ['actions'] обращается к значению ключа actions . [1] обращается ко второму словарю в этом списке. ['value'] обращается к значению ключа value .