Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/313.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python df.drop(如果存在)_Python_Pandas - Fatal编程技术网

Python df.drop(如果存在)

Python df.drop(如果存在),python,pandas,Python,Pandas,下面是一个函数,它接受一个文件并删除列名“row_num”、“start_date”、“end_date” 问题是不是每个文件都有这些列名,所以函数返回一个错误 我的目标是修改代码,以便在存在这些列时删除这些列,但在该列不存在时不返回错误 def read_df(file): df = pd.read_csv(file, na_values=['', ' ']) # Drop useless junk and fill empty values with zero df

下面是一个函数,它接受一个文件并删除列名“row_num”、“start_date”、“end_date”

问题是不是每个文件都有这些列名,所以函数返回一个错误

我的目标是修改代码,以便在存在这些列时删除这些列,但在该列不存在时不返回错误

def read_df(file):
    df = pd.read_csv(file, na_values=['', ' '])
    # Drop useless junk and fill empty values with zero 
    df = df.drop(['row_num','start_date','end_date','symbol'], axis=1).fillna(0)
    df=df[df!=0][:-1].dropna().append(df.iloc[-1])
    return df

将参数
错误
添加到:

错误:{'ignore','raise'},默认为'raise'

如果“忽略”,则抑制错误并仅删除现有标签

样本

df = pd.DataFrame({'row_num':[1,2], 'w':[3,4]})
df = df.drop(['row_num','start_date','end_date','symbol'], axis=1, errors='ignore')
print (df)
   w
0  3
1  4
要检查列是否存在,可以执行以下操作:

for i in x:
    if i in df:
        df = df.drop(['row_num','start_date','end_date','symbol'], axis=1).fillna(0)


我只是不得不这么做;以下是我所做的:

# Drop these columns if they exist
cols = ['Billing Address Street 1', 'Billing Address Street 2','Billing Company']
for col in cols:
    if col in df.columns:
        df = df.drop(columns=col, axis=1)

可能不是最好的方法,但它达到了目的。

在我的测试中,以下速度至少与给出的任何答案一样快:

candidates=['row_num','start_date','end_date','symbol']
df = df.drop([x for x in candidates if x in df.columns], axis=1)
它具有可读性的优点,并且(对代码进行了一点小的调整)能够准确地记录哪些列在出现时存在/被删除

一些原因可能比以前的解决方案更可取:

  • 在项目上循环并单独删除每个列(如果存在的话)是可行的,但速度相当慢(参见下面的基准测试)
  • jezrael的回答很好,但一开始让我感到紧张(忽略错误感觉很糟糕!)。进一步查看文档,听起来这似乎没问题,只是忽略了不存在的列的错误(而不是其他不希望忽略的错误)。我的解决方案可能更具可读性,特别是对于那些不太熟悉熊猫中可选Kwarg的人
基准结果:

基准测试代码(关于如何创建此类基准,请参见中的答案):


Try except就是为了这个,我认为你的想法是正确的,但是实现是错误的……你在x中删除了所有内容,如果任何项目在df.columns(不是全部)中,你没有引用x。定义x之后,你应该改为执行
x=[i for i in x if i in df.columns]
,或者使用交集,然后你可以删除x。
for i in x:
    if i in df.columns:
        df = df.drop(['row_num','start_date','end_date','symbol'], axis=1).fillna(0)
# Drop these columns if they exist
cols = ['Billing Address Street 1', 'Billing Address Street 2','Billing Company']
for col in cols:
    if col in df.columns:
        df = df.drop(columns=col, axis=1)
candidates=['row_num','start_date','end_date','symbol']
df = df.drop([x for x in candidates if x in df.columns], axis=1)
import math
from simple_benchmark import benchmark
import pandas as pd

# setting up the toy df:
def df_creator(length):
    c1=list(range(0,10))
    c2=list('a,b,c,d,e'.split(','))
    c3=list(range(0,5))
    c4=[True,False]
    lists=[c1,c2,c3,c4]
    df=pd.DataFrame()
    count=0
    for x in lists:
        count+=1
        df['col'+str(count)]=x*math.floor(length/len(x))
    return df

# setting up benchmark test:
def list_comp(df,candidates=['col1','col2','col5','col8']):
    return df.drop([x for x in candidates if x in df.columns], axis=1)

def looper(df,candidates=['col1','col2','col5','col8']):
    for col in candidates:
        if col in df.columns:
            out = df.drop(columns=col, axis=1)
    return out

def ignore_error(df,candidates=['col1','col2','col5','col8']):
    return df.drop(candidates, axis=1, errors='ignore')

functions=[list_comp,looper,ignore_error]

args={n : df_creator(n) for n in [10,100,1000,10000,100000]}
argname='df_length'
b=benchmark(functions,args,argname)
b.plot()