python - 如何优化以下代码?

标签 python pandas

我正在用 python 编写一个程序来替换数据框的一些值,我的想法是我有一个名为 file.txt 的文件,看起来像这样:

A:s:Y:0.1:0.1:0.1:0.2:0.1
B:r:D:0.3:0.5:0.1:0.2:0.2
C:f:C:0.3:0.4:0.2:-0.1:0.4
D:f:C:0.1:0.2:0.1:0.1:0.1
F:f:C:0.1:-0.1:-0.1:0.1:0.1
G:f:C:0.0:-0.1:0.1:0.3:0.4
H:M:D:0.1:0.4:0.1:0.0:0.4

我想使用 ':::' 作为分隔符,我想按照以下规则为某些字符串替换四列的值:

所有属于 range1 的值都将被替换为“N”:

range1=[-0.2,-0.1,0,0.1,0.2] -> 'N'

所有属于 range2 的值都将被替换为“L”:

range2=[-0.5,-0.4,-0.3] -> 'L'

所有属于 range3 的值都将被替换为“H”:

range3=[0.3,0.4,0.5]

为了实现这一点,我尝试了以下方法:

import pandas as pd

df= pd.read_csv('file.txt', sep=':',header=None)

labels=df[3]


range1=[-0.2,-0.1,0,0.1,0.2]

range2=[-0.5,-0.4,-0.3]

range3=[0.3,0.4,0.5]

lookup = {'N': range1, 'L': range2, 'H': range3}




for k, v in lookup.items():
    df.loc[df[3].isin(v), 3] = k


for k, v in lookup.items():
    df.loc[df[4].isin(v), 4] = k


for k, v in lookup.items():
    df.loc[df[5].isin(v), 5] = k

for k, v in lookup.items():
    df.loc[df[6].isin(v), 6] = k

for k, v in lookup.items():
    df.loc[df[7].isin(v), 7] = k


print(df)

它工作得很好,但我想避免使用这么多 for,我想感谢任何关于如何实现这一目标的建议。

最佳答案

您可以使用 where 代替:

for k, v in lookup.items():
    df = df.where(~df.isin(v), k)

这表示在 v 中不包含 df 的值时保留这些值。否则,将它们替换为值 k。分配在每次迭代时覆盖 df 以累积分类标签。

此方法适用于一次操作中的所有列,因此仅当您想用其分类编码字母替换给定数值的每个实例时才适用。

where 有另一个选项指定就地修改,但不幸的是它不能与具有混合列类型的 DataFrame 一起使用。在您的示例中,第 0、1 和 2 列的类型为 object,而其余列的类型为 float。因此,pandas 保守地(并且效率低下)假设它必须将所有内容转换为 object 以进行就地覆盖,并引发 TypeError而不是进一步检查以查看是否只有相同类型的列实际上受到了突变的影响。

例如,这个:

df.where(~df.isin(v), k, inplace=True)

将引发 TypeError

Pandas 的这种限制相当令人沮丧。例如,您也不能使用常规的 pandas 赋值来解决它,因为下面也会给出相同的 TypeError:

for k, v in lookup.items():
    df.where(~df.isin(v), inplace=True)
    df[df.isnull()] = k # <-- same TypeError  

并且令人惊奇地将 try_cast 关键字参数设置为 True 和/或将 raise_on_error 关键字参数设置为 False不影响是否引发 TypeError,因此您不能在使用 where 时禁用此类型安全检查。

关于python - 如何优化以下代码?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36723702/

相关文章:

python - 通过整数索引选择一行 Pandas 系列/数据框

python - 根据使用多列的条件聚合 Pandas DataFrame?

c++ - Python 到 C++ : From Deriv, 到 Base,再到 Deriv

python - 如何将系列值分配给数据框的列名称

python - Windows 上的导入和路径名

python-3.x - 每 n 个字符拆分一个 pandas 列

python - 如何使用数据框创建不确定长度的Excel电子表格?

python - 将 series.rolling 的输出修改为小数点后 2 位

Python/BeautifulSoup - 提取 div 内容检查 h1 文本

python - 在 python 中嵌套数值积分