Как превратить список списка словарей в цикл данных с помощью цикла - PullRequest
1 голос
/ 24 мая 2019

У меня есть список из списка словарей.Мне удалось получить доступ к каждому элементу списка во внешнем списке и преобразовать словарь через панд в фрейм данных.Затем я сохраняю DF, а затем записываю его.Это идеальный результат.Но мне нужен цикл, чтобы сделать это для больших данных.

Вот мой MWE, который в принципе работает нормально.

import pandas as pd

mwe = [
    [{"name": "Norway", "population": 5223256, "area": 323802.0, "gini": 25.8}],
    [{"name": "Switzerland", "population": 8341600, "area": 41284.0, "gini": 33.7}],
    [{"name": "Australia", "population": 24117360, "area": 7692024.0, "gini": 30.5}],
]

df0 = pd.DataFrame.from_dict(mwe[0])
df1 = pd.DataFrame.from_dict(mwe[1])
df2 = pd.DataFrame.from_dict(mwe[2])

frames = [df0, df1, df2]
result = pd.concat(frames)

Он создает хорошую таблицу.

enter image description here

Вот что я пытался создать список фреймов данных:

for i in range(len(mwe)): 
    frame = pd.DataFrame()
    frame = pd.DataFrame.from_dict(mwe[i])
    frames = []
    frames.append(frame)

Добавление: Спасибо за все ответы.Они работают на моем MWE.Что заставило меня заметить, что в моем наборе данных есть несколько странных записей.Решение для моего набора данных не работает, поскольку у меня есть элемент внутреннего списка, который содержит два словаря (из-за неуникального извлечения данных):

.... [{'name': 'Малые отдаленные острова США',' население ': 300}, {' имя ':' Соединенные Штаты Америки ',' население ': 323947000,' область ': 9629091.0,' джини ': 48.0}], ...

Как я могу удалить запись для "Малые отдаленные острова США"?

Ответы [ 3 ]

4 голосов
/ 24 мая 2019

Вы можете получить каждый диктовку из содержащего списка и просто иметь list из dict:

import pandas as pd
mwe = [[{'name': 'Norway', 'population': 5223256, 'area': 323802.0, 'gini': 25.8}],
 [{'name': 'Switzerland',
   'population': 8341600,
   'area': 41284.0,
   'gini': 33.7}],
 [{'name': 'Australia',
   'population': 24117360,
   'area': 7692024.0,
   'gini': 30.5}]]

# use x.pop() so that you aren't carrying around copies of the data
# for a "big data" application
df = pd.DataFrame([x.pop() for x in mwe])


df.head()
        area  gini         name  population
0   323802.0  25.8       Norway     5223256
1    41284.0  33.7  Switzerland     8341600
2  7692024.0  30.5    Australia    24117360

Включив понимание списка в объявление dataframe, этот список является временным, и вам не нужно беспокоиться об очистке. pop также будет использовать словари из mwe, минимизируя количество копий, которые вы носите в памяти

Как примечание, при этом mwe будет выглядеть так:

mwe
[[], [], []]

Поскольку содержимое подсписков выскочило

РЕДАКТИРОВАТЬ: новый вопрос содержание

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

mwe.append([{'name': 'United States Minor Outlying Islands', 'population': 300}, {'name': 'United States of America', 'population': 323947000, 'area': 9629091.0, 'gini': 48.0}])

key_check = {}.fromkeys(["name", "population", "area", "gini"])

# the easy way but copies data
df = pd.DataFrame([item for item in data
                   for data in mwe 
                   if item.keys()==key_check.keys()])

Поскольку данные по-прежнему будут висеть в mwe. Может быть лучше использовать генератор

def get_filtered_data(mwe):
    for data in mwe:
        while data: # when data is empty, the while loop will end
            item = data.pop() # still consumes data out of mwe
            if item.keys() == key_check.keys():
                yield item    # will minimize data copying through lazy evaluation

df = pd.DataFrame([x for x in get_filtered_data(mwe)])

        area  gini                      name  population
0   323802.0  25.8                    Norway     5223256
1    41284.0  33.7               Switzerland     8341600
2  7692024.0  30.5                 Australia    24117360
3  9629091.0  48.0  United States of America   323947000

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

1 голос
/ 24 мая 2019

Попробуйте:

df = pd.DataFrame(columns = ['name', 'population', 'area', 'gini'])
for i in range(len(mwe)):
    df.loc[i] = list(mwe[i][0].values())

Вывод :

          name       pop       area  gini
0       Norway   5223256   323802.0  25.8
1  Switzerland   8341600    41284.0  33.7
2    Australia  24117360  7692024.0  30.5
1 голос
/ 24 мая 2019

Создание и очистка DataFrame и цикл по списку, используя df.append в каждом цикле:

>>> import pandas as pd
    mwe = [[{'name': 'Norway', 'population': 5223256, 'area': 323802.0, 'gini': 25.8}],
     [{'name': 'Switzerland',
       'population': 8341600,
       'area': 41284.0,
       'gini': 33.7}],
     [{'name': 'Australia',
       'population': 24117360,
       'area': 7692024.0,
       'gini': 30.5}]]

>>> df = pd.DataFrame()                                                                                                                                                                   

>>> for country in mwe: 
...     df = df.append(country) 
...

>>> df
            area  gini         name  population
    0   323802.0  25.8       Norway     5223256
    0    41284.0  33.7  Switzerland     8341600
    0  7692024.0  30.5    Australia    24117360
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...