Python 基于列值对数据帧值进行二值化

Python 基于列值对数据帧值进行二值化,python,pandas,Python,Pandas,我有一个像这样的数据框 +---------+-------------+------------+------------+ | hello | val1 | val2 | val3 | +---------+-------------+------------+------------+ | 1.024 | -10.764779 | -8.230176 | -5.689302 | | 16 | -15.772744 | -10.

我有一个像这样的数据框

+---------+-------------+------------+------------+
| hello   | val1        | val2       | val3       |
+---------+-------------+------------+------------+
| 1.024   | -10.764779  | -8.230176  | -5.689302  |
| 16      | -15.772744  | -10.794013 | -5.79148   |
| 1.024   | -18.4738    | -13.935423 | -9.392713  |
| 0.064   | -11.642506  | -9.711523  | -7.772969  |
| 1.024   | -4.185368   | -2.094441  | 0.048861   |
+---------+-------------+------------+------------+
让此数据帧为
df
。这是我基本上想做的手术

values = ["val1", "val2", "val3"]
for ind in df.index:
    hello = df.loc[ind, "hello"]
    for name in values:
        df.loc[ind, name] = (df.loc[ind, name] >= hello)
基本上,对于每一行
i
和每一列
j
,如果
val\u j
小于
hello\u i
,则
val\u j=False
,否则
val\u j=True

这显然不是矢量化的,由于我的电脑上有这个表格的巨大版本,我的电脑在执行这些修改时遇到了问题


上面操作的矢量化版本是什么?

一些实验让我想到了这一点

column_names = [name for name in df.columns if "val" in name]
binarized = df.apply(lambda row : row[column_names] >= row["hello"], axis=1)
df[binarized.columns] = binarized

这是可行的。

根据hello系列测试整个系列会更快:

In [268]:

val_cols = [col for col in df if 'val' in col]
for col in val_cols:
    df[col] = df[col] >= df['hello']
df    
Out[268]:
    hello   val1   val2   val3
0   1.024  False  False  False
1  16.000  False  False  False
2   1.024  False  False  False
3   0.064  False  False  False
4   1.024  False  False  False
如果我们比较性能:

In [273]:

%%timeit
val_cols = [col for col in df if 'val' in col]
for col in val_cols:
    df[col] = df[col] >= df['hello']
df    
1000 loops, best of 3: 630 µs per loop
In [275]:

%%timeit
column_names = [name for name in df.columns if "val" in name]
binarized = df.apply(lambda row : row[column_names] >= row["hello"], axis=1)
df[binarized.columns] = binarized
df
100 loops, best of 3: 6.17 ms per loop

我们看到我的方法是矢量化的10倍,你的方法基本上是在每一行上循环

有什么理由做这些操作
行操作
,而不是
列操作
?在我看来,您似乎可以一次性计算整个列的val_j_binary。@cel column-wise?我们根据行上的值而不是列上的值,将单元格计算为
True
False
。我不知道你的问题是什么。很抱歉,如果现有列大于或等于hello列,你是否要用True或False覆盖它们?@EdChum:是的。抱歉,我不理解您之前的评论,即如果这是一个
列操作
操作,它会更快。@hlin117我的回答显示了一种不同的方法,它明显更快。我知道pandas中的
for
循环会比它的一个内置函数更快。非常感谢。for循环不是这里的关键,主要的一点是我们在整个系列上操作,您通过了
axis=1
,因此实际上您在每行的每个条目上执行for循环。如果行数少于列数,这可能是一种较慢的方法。但是是的,您关于
axis=1
的评论是正确的。如果我想存储
0
1
,而不是
False
True
,我该怎么做呢?没关系
df[val\u cols]=df[val\u cols].astype(int)
成功了。