如何将模型对象列表转换为pandas dataframe?

eza*_*mur 30 python numpy pandas

我有这个类的对象数组

class CancerDataEntity(Model):

    age = columns.Text(primary_key=True)
    gender = columns.Text(primary_key=True)
    cancer = columns.Text(primary_key=True)
    deaths = columns.Integer()
    ...
Run Code Online (Sandbox Code Playgroud)

打印时,数组看起来像这样

[CancerDataEntity(age=u'80-85+', gender=u'Female', cancer=u'All cancers (C00-97,B21)', deaths=15306), CancerDataEntity(...
Run Code Online (Sandbox Code Playgroud)

我想将它转换为数据框,这样我就可以用更合适的方式来玩它 - 聚合,计数,求和等.我希望这个数据框看起来像这样:

     age     gender     cancer     deaths
0    80-85+  Female     ...        15306
1    ...
Run Code Online (Sandbox Code Playgroud)

有没有办法轻松地使用numpy/pandas实现这一点,而无需手动处理输入数组?

Ore*_*ail 41

更简洁的方法是to_dict在类上定义一个方法然后使用pandas.DataFrame.from_records

class Signal(object):
    def __init__(self, x, y):
        self.x = x
        self.y = y

    def to_dict(self):
        return {
            'x': self.x,
            'y': self.y,
        }
Run Code Online (Sandbox Code Playgroud)

例如

In [87]: signals = [Signal(3, 9), Signal(4, 16)]

In [88]: pandas.DataFrame.from_records([s.to_dict() for s in signals])
Out[88]:
   x   y
0  3   9
1  4  16
Run Code Online (Sandbox Code Playgroud)

  • 对于没有任何`__dict__`技巧的简单类,这可以简化为`pandas.DataFrame([vars(s)for s in signals])`而不实现自定义`to_dict`函数. (5认同)
  • 很棒的答案!但请注意,我在不使用`from_records`的情况下得到了相同的结果:`pandas.DataFrame([s.to_dict()用于信号中的s]) (2认同)

eza*_*mur 20

导致期望结果的代码:

variables = arr[0].keys()
df = pd.DataFrame([[getattr(i,j) for j in variables] for i in arr], columns = variables)
Run Code Online (Sandbox Code Playgroud)

感谢@Serbitar指出我正确的方向.


typ*_*n04 17

我想强调Jim Hunziker的评论。

pandas.DataFrame([vars(s) for s in signals])
Run Code Online (Sandbox Code Playgroud)

编写起来要容易得多,更不容易出错,而且to_dict()每次添加新属性时都不必更改函数。

如果您希望自由选择要保留的属性,则可以使用columns参数。

pandas.DataFrame([vars(s) for s in signals], columns=['x', 'y'])
Run Code Online (Sandbox Code Playgroud)

缺点是它不适用于复杂的属性,尽管这种情况很少发生。


Ser*_*tar 10

尝试:

variables = list(array[0].keys())
dataframe = pandas.DataFrame([[getattr(i,j) for j in variables] for i in array], columns = variables)
Run Code Online (Sandbox Code Playgroud)

  • http://meta.stackoverflow.com/questions/262695/new-answer-deletion-option-code-only-answer (2认同)

Shi*_*hah 5

你可以做,

import pandas as pd

# define some class
class SomeThing:
    def __init__(self, x, y):
        self.x, self.y = x, y

# make an array of the class objects
things = [SomeThing(1,2), SomeThing(3,4), SomeThing(4,5)]

# fill dataframe with one row per object, one attribute per column
df = pd.DataFrame([t.__dict__ for t in things ])

print(df)
Run Code Online (Sandbox Code Playgroud)

打印:

   x  y
0  1  2
1  3  4
2  4  5
Run Code Online (Sandbox Code Playgroud)