shell标准输出PYTHON处理比PYTHON txt文件处理慢得多

2024-09-28 23:44:37 发布

您现在位置:Python中文网/ 问答频道 /正文

我正在执行一项任务,解析/处理从unixshell生成的“大型”原始数据。需要对这些原始数据进行解析,以将其从一些特殊字符中清除

最后,我想做的是避免需要大的临时文件,而是在运行中这样做

方式1生成一个大的8GB临时文本文件(不需要),但速度很快(8分钟完成执行): 首先,我生成一个临时原始文本文件(我将shell输出放入一个txt文件),然后使用以下代码进行解析: 执行时间8分钟输出文件大小800MB:

f = open(filepath, 'r')
fOut= open(filepathOut,"w+")
for line in f:
    if len(line) > 0:
        if "RNC" in line:
            rncflag = 1
            #quito enter, quito cadena a la izquierda y quito comillas a la derecha
            currline = line.strip('\n').strip('\t').replace(".",",").replace(" ","").lstrip(";")
        else:
            currline = line.strip('\n').strip('\t').replace(".",",").replace(" ","").lstrip(";")

        if rncflag == 1:
            if lineNumOne == 1:
                processedline = currline
                lineNumOne = 0
            else:
                processedline = '\n' + currline
            rncflag = 0
        else:
            processedline = currline

    fOut.write(processedline)
fOut.close()

方式2,直接从stdout飞行(约1.5小时完成执行): 是我更喜欢的一个,因为我不需要生成之前的原始文件进行解析。 我使用子进程库在生成stdoutunixshell时直接逐行解析/处理它(就像它在txt文件的行中)。 问题是,这比前面的方法慢得多。 获取相同输出文件(大小800MB)的执行时间超过1,5小时:

cmd = subprocess.Popen(isqlCmd, shell=True, stdout=subprocess.PIPE)
for line in cmd.stdout:
    if len(line) > 0:
        if "RNC" in line:
            rncflag = 1
            #quito enter, quito cadena a la izquierda y quito comillas a la derecha
            currline = line.strip('\n').strip('\t').replace(".",",").replace(" ","").lstrip(";")
        else:
            currline = line.strip('\n').strip('\t').replace(".",",").replace(" ","").lstrip(";")

        if rncflag == 1:
            if lineNumOne == 1:
                processedline = currline
                lineNumOne = 0
            else:
                processedline = '\n' + currline
            rncflag = 0
        else:
            processedline = currline

    fOut.write(processedline)

fOut.close()

我不是python专家,但我相信如果unix标准输出是动态的,那么有一种方法可以加快处理速度,而不是以前生成原始文件,然后在生成原始文件后对其进行解析

该程序的目的是清理/解析sybase isql查询输出。注意:无法安装sybase库

Python版本是->;Python 2.6.4无法更改它

提前感谢,欢迎任何改进


Tags: 文件iniflineelselareplacestrip
1条回答
网友
1楼 · 发布于 2024-09-28 23:44:37

如果没有重现问题的能力,标准答案是不可行的,但可以提供缩小问题范围所需的工具

如果您从使用subprocess.Popen(..., stdout=subprocess.PIPE)切换到仅无条件地从sys.stdin读取,这意味着我们可以在从文件读取案例(在这种情况下,您希望运行./yourscript <inputfile)以及从进程读取管道案例(./runIsqlCommand | ./yourscript)中使用相同的代码,因此我们可以确信我们正在进行类似的测试

一旦完成,它还为我们提供了放置缓冲的空间,以防止管道两侧不必要地相互阻塞。要执行此操作,请执行以下操作:

./runIsqlCommand | pv | ./yourscript

…其中pvPipe Viewer,这是一个工具,它既提供了一个进度条(当内容总量已知时)、一个吞吐量指示器,也提供了一个比操作系统默认值大得多的缓冲区,以及进一步调整该大小的空间(和监视消耗)

要确定Python脚本的运行速度是否比SQL代码慢,请告诉pv使用-T参数显示缓冲区消耗。(如果显示,则pv正在使用splice()系统调用在进程之间直接传输内容,而不实际执行缓冲;-C参数将增加pv的开销,但确保它实际能够执行缓冲并报告缓冲区内容)。如果缓冲区几乎一直是100%满的,那么我们知道SQL的生成速度比Python读取的速度快;如果它通常是空的,那么我们知道Python正在跟上

相关问题 更多 >