Как создать и заполнить pandas dataframe из цикла for?

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

for p in game.players.passing():
    print p, p.team, p.passing_att, p.passer_rating()

R.Wilson SEA 29 55.7
J.Ryan SEA 1 158.3
A.Rodgers GB 34 55.8

Используя этот код:

d = []
for p in game.players.passing():
    d = [{'Player': p, 'Team': p.team, 'Passer Rating':
        p.passer_rating()}]

pd.DataFrame(d)

Я могу получить:

    Passer Rating   Player      Team
  0 55.8            A.Rodgers   GB

Какой размер кадра 1x3, и я понимаю, почему это только одна строка, но я не могу понять, как сделать ее многострочной с столбцами в правильном порядке. В идеале решение могло бы иметь дело с n количеством строк (на основе p), и было бы замечательно (хотя и не обязательно), если бы количество столбцов было задано по количеству запрошенных статистических данных. Какие-либо предложения? Спасибо заранее!

Ответ 1

Попробуйте это, используя понимание списка:

from pandas import DataFrame as df

d = df[[p, p.team, p.passing_att, p.passer_rating()] for p in game.players.passing()]

Ответ 2

Самый простой ответ - это то, что сказал Пол Х:

d = []
for p in game.players.passing():
    d.append({'Player': p, 'Team': p.team, 'Passer Rating':
        p.passer_rating()})

pd.DataFrame(d)

Но если вы действительно хотите "создать и заполнить dataframe из цикла" (что, кстати, я бы не рекомендовал), вот как вы это сделаете.

d = pd.DataFrame()

for p in game.players.passing():
    temp = pd.DataFrame({'Player': p, 'Team': p.team, 'Passer Rating':
        p.passer_rating()})

    d = pd.concat([d, temp])

Ответ 3

Составьте список кортежей с вашими данными, а затем создайте с ним DataFrame:

d = []
for p in game.players.passing():
    d.append((p, p.team, p.passer_rating()))

pd.DataFrame(d, columns=('Player', 'Team', 'Passer Rating'))

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

Функции тестирования:

def with_tuples(loop_size=1e5):
    res = []

    for x in range(int(loop_size)):
        res.append((x-1, x, x+1))

    return pd.DataFrame(res, columns=("a", "b", "c"))

def with_dict(loop_size=1e5):
    res = []

    for x in range(int(loop_size)):
        res.append({"a":x-1, "b":x, "c":x+1})

    return pd.DataFrame(res)

Результаты:

%timeit -n 10 with_tuples()
# 10 loops, best of 3: 55.2 ms per loop

%timeit -n 10 with_dict()
# 10 loops, best of 3: 130 ms per loop

Ответ 4

Я могу ошибаться, но я думаю, что принятый ответ @amit содержит ошибку.

from pandas import DataFrame as df
x = [1,2,3]
y = [7,8,9,10]

# this gives me a syntax error at 'for' (Python 3.7)
d1 = df[[a, "A", b, "B"] for a in x for b in y]

# this works
d2 = df([a, "A", b, "B"] for a in x for b in y)

# and if you want to add the column names on the fly
# note the additional parentheses
d3 = df(([a, "A", b, "B"] for a in x for b in y), columns = ("l","m","n","o"))