遍历 pyspark 数据框列

Posted

技术标签:

【中文标题】遍历 pyspark 数据框列【英文标题】:iterate over pyspark dataframe columns 【发布时间】:2017-02-17 21:47:31 【问题描述】:

我有以下pyspark.dataframe

age  state  name    income
21    DC    john    30-50K
NaN   VA    gerry   20-30K

我正在尝试实现相当于 df.isnull().sum()(来自 pandas)的效果:

age      1
state    0
name     0
income   0

起初我尝试了一些类似的东西:

null_counter = [df[c].isNotNull().count() for c in df.columns]

但这会产生以下错误:

TypeError: Column is not iterable

同样,这就是我当前迭代列以获得最小值的方式:

class BaseAnalyzer:
    def __init__(self, report, struct):
        self.report = report
        self._struct = struct
        self.name = struct.name
        self.data_type = struct.dataType
        self.min = None
        self.max = None

    def __repr__(self):
        return '<Column: %s>' % self.name


class BaseReport:
    def __init__(self, df):
        self.df = df
        self.columns_list = df.columns
        self.columns = f.name: BaseAnalyzer(self, f) for f in df.schema.fields

    def calculate_stats(self):
        find_min = self.df.select([fn.min(self.df[c]).alias(c) for c in self.df.columns]).collect()
        min_row = find_min[0]
        for column, min_value in min_row.asDict().items():
            self[column].min = min_value

    def __getitem__(self, name):
        return self.columns[name]

    def __repr__(self):
        return '<Report>'

report = BaseReport(df)
calc = report.calculate_stats()

for column in report1.columns.values():
if hasattr(column, 'min'):
    print(":".format(column, column.min))

这允许我“遍历列”

<Column: age>:1
<Column: name>: Alan
<Column: state>:ALASKA
<Column: income>:0-1k

我认为这种方法已经变得很复杂,我怎样才能正确地遍历所有列以提供各种汇总统计信息(最小值、最大值、isnull、notnull 等)。pyspark.sql.Rowpyspark.sql.Column 之间的区别似乎来自熊猫的奇怪。

【问题讨论】:

【参考方案1】:

你有没有尝试过这样的事情:

names = df.schema.names
for name in names:
    print(name + ': ' + df.where(df[name].isNull()).count())

您可以看到如何修改它以将信息放入字典或其他更有用的格式。

【讨论】:

这看起来很有希望,尽管我最终得到了 TypeError: Can't convert 'method' object to str implicitly 我的架构如下:['individual_id', 'first_name', 'last_name', 'house_number', 'street_name', 'city', 'state', 'zip', 'county_name', 'age', 'gender', 'birthdate', 'null_col', 'ind_politicalparty', 'ind_vendorethnicity', 'dma', 'cd', 'hh_income'] 所以看起来底层的str 类型在这一点上或多或少地导致了问题?编辑后错误变为TypeError: Can't convert 'int' object to str implicitly 感谢您的帮助! 这很奇怪。我使用您在问题中显示的值创建了一个 df 并且一切都按预期工作。似乎其中一列中可能存在某种混合数据类型。 hmm...您可能是对的,因为另一列中还有其他数据类型,我提供了一个示例,该示例不包括我正在使用的所有类型(几乎是每种类型)我想知道是否需要事先Column.cast【参考方案2】:

你可以试试这个:

nullDf= df.select([count(when(col(c).isNull(), c)).alias(c) for c in df.columns]) 
nullDf.show() 

它将为您提供一个列的列表,其中包含 null 其 null 值的数量。

【讨论】:

以上是关于遍历 pyspark 数据框列的主要内容,如果未能解决你的问题,请参考以下文章

python, pyspark : 获取 pyspark 数据框列值的总和

使用圆形函数转换 pyspark 数据框列不起作用(pyspark)

如何将 pyspark 数据框列中的值与 pyspark 中的另一个数据框进行比较

更新 pyspark 的数据框列

数据类型转换火花数据框列 - pyspark

Pyspark 删除数据框列中的多个字符