在 Pandas 中使用 iterrows 的有效方法(另一种方式)

麦克斯

这是我在论坛上的第一个问题。谢谢你的帮助!

我基于 df.iterrows () (sic.) 编写了嵌套的 for 循环,它需要花费大量的时间来执行。我需要通过检查描述条件下的所有单元格来将一个数据帧的值分配给另一个数据帧。你能帮我让它有效吗?(多处理、应用方法、矢量化或其他任何东西?)将不胜感激!:)

样本数据:

import pandas as pd
import numpy as np

d1 = {'geno_start' : [60, 1120, 1660], 'geno_end' : [90, 1150, 1690], 'original_subseq' : ['AAATGCCTGAACCTTGGAATTGGA',  'AAATGCCTGAACCTTGGAATTGGA', 'AAATGCCTGAACCTTGGAATTGGA']}

d2 = {'most_left_coordinate_genome' : [56, 1120, 1655], 'most_right_coordinate_genome' : [88, 1150, 1690], 'protein_ID' : ['XYZ_1', 'XYZ_2', 'XYZ_3']}

df_1 = pd.DataFrame(data=d1)
df_2 = pd.DataFrame(data=d2)

df_1['protein_ID'] = np.nan


def match_ranges(df1: pd.DataFrame, df2: pd.DataFrame):

for index, row_2 in df2.iterrows():
    for index_1, row_1 in df1.iterrows():
        if (row_1['geno_start'] >= row_2['most_left_coordinate_genome']) & (row_1['geno_end'] <= row_2['most_right_coordinate_genome']):
            df1['protein_ID'].iloc[index_1] = row_2['protein_ID']
                
        elif (abs(row_1['geno_start'] - row_2['most_left_coordinate_genome']) < 30) & (row_1['geno_end'] <= row_2['most_right_coordinate_genome']):
            df1['protein_ID'].iloc[index_1] = row_2['protein_ID']
                
        elif (row_1['geno_start'] >= row_2['most_left_coordinate_genome']) & (abs(row_1['geno_end'] - row_2['most_right_coordinate_genome']) < 30):
            df1['protein_ID'].iloc[index_1] = row_2['protein_ID']

match_ranges(df_1, df_2)

期望的输出:

知乎

这是一种从 2 个 for 循环到 1 个循环的方法。我重命名了几列以减少线宽。

首先,创建数据框:

import pandas as pd

d1 = {'geno_start' : [60, 1120, 1660], 
      'geno_end' : [90, 1150, 1690], 
      'original_subseq' : ['AAATGCCTGAACCTTGGAATTGGA',  
                           'AAATGCCTGAACCTTGGAATTGGA', 
                           'AAATGCCTGAACCTTGGAATTGGA'],}
d2 = {'left' : [56, 1120, 1655], 
      'right' : [88, 1150, 1690], 
      'protein_ID' : ['XYZ_1', 'XYZ_2', 'XYZ_3']}
df_1 = pd.DataFrame(data=d1)
df_1['protein_ID'] = '?'
df_1['rule'] = '?'
df_2 = pd.DataFrame(data=d2)

其次,填充protein_ID第一个数据框中列(即,基因组开始,基因组结束):

for g in df_1.itertuples():
    
    # Rule A: left most <= geno start < geno end <= right-most
    # LM-----------------------RM   left- and right-most
    #     GS-----------GE           genome start, end
    if ((df_2['left'] <= g.geno_start) & (g.geno_end <= df_2['right'])).any():
        mask = (df_2['left'] <= g.geno_start) & (g.geno_end <= df_2['right'])
        df_1.at[g.Index, 'protein_ID'] = df_2.loc[mask, 'protein_ID'].values[0]
        df_1.at[g.Index, 'rule'] = 'Rule A'
        
        
    # Rule B: geno start before left-most
    #      LM-----------------RM
    #  GS-----------------GE
    elif ((df_2['left'] - g.geno_start < 30) & (g.geno_end <= df_2['right'])).any():
        mask = (df_2['left'] - g.geno_start < 30) & (g.geno_end <= df_2['right'])
        df_1.at[g.Index, 'protein_ID'] = df_2.loc[mask, 'protein_ID'].values[0]
        df_1.at[g.Index, 'rule'] = 'Rule B'

    # Rule C: geno end after right-most 
    #      LM-----------------RM
    #          GS-----------------GE

    elif ((df_2['left'] <= g.geno_start) & (g.geno_end - df_2['right'] < 30)).any():
        mask = (df_2['left'] <= g.geno_start) & (g.geno_end - df_2['right'] < 30)
        df_1.at[g.Index, 'protein_ID'] = df_2.loc[mask, 'protein_ID'].values[0]
        df_1.at[g.Index, 'rule'] = 'Rule C'
        
    else:
        pass

print(df_1)
   geno_start  geno_end           original_subseq protein_ID    rule
0          60        90  AAATGCCTGAACCTTGGAATTGGA      XYZ_1  Rule C
1        1120      1150  AAATGCCTGAACCTTGGAATTGGA      XYZ_2  Rule A
2        1660      1690  AAATGCCTGAACCTTGGAATTGGA      XYZ_3  Rule A

本文收集自互联网,转载请注明来源。

如有侵权,请联系 [email protected] 删除。

编辑于
0

我来说两句

0 条评论
登录 后参与评论

相关文章

在 Pandas 中使用 iterrows() 和算术

Python Pandas Iterrows方法

Pandas:使用 iterrows 应用更改

如何使用pandas apply来替换iterrows?

使用pandas选择多列和fillna()的另一种方法

使用.iterrows()以更干净的方式遍历pandas dateframe中的行,并跟踪特定值之间的行

在Python中使用PANDAS iterrows()时索引未从零开始

在另一种方法中使用Return

在另一种方法中使用int

python和pandas-如何使用iterrows访问列

使用 iterrows 选择 Pandas 数据框中的下 N 行

带有 iterrows() 的 Pandas for 循环和数据帧的命名

在没有 iterrows 的情况下更新 Pandas 行

防止在另一种方法中使用一种方法

Python-Pandas Group by Iterrows

Docker中的Pandas iterrows()太慢

在熊猫中使用iterrows进行循环

有另一种方式在java中11使用这个布尔?

Panda Dataframe - 使用 .iterrows() 有没有更好的方法?

还有另一种方法可以使用有效时间更长的URL将收件人视图嵌入到应用程序中?

需要另一种方式在 PostgreSQL 中使用表名作为函数参数

还有另一种在Java中使用hasNextInt()而不将所有内容置于if语句中的方法吗?

Python-使用.iterrows()以外的方法遍历数据框

如何在另一种方法中使用一种方法的“返回”值

在 Python 中的另一种方法中使用一种方法中的变量

将值从一种方法返回到另一种方法以在输出中使用

在另一种方法中使用一个变量参数

如何在另一种方法的方法中使用来自 HashMap 的数据?

迭代 Pandas 中數據幀中的行:使用 df.index 和 df.iterrows() 作為迭代器有區別嗎?