【问题标题】:Open file, read it, process, and write back - shortest method in Python打开文件、读取、处理和回写 - Python 中最短的方法
【发布时间】:2010-09-18 15:40:59
【问题描述】:

我想对文件进行一些基本过滤。读取它,进行处理,然后写回它。

我不是在寻找“打高尔夫球”,而是想要最简单、最优雅的方法来实现这一目标。我想出了:

from __future__ import with_statement

filename = "..." # or sys.argv...

with open(filename) as f:
    new_txt = # ...some translation of f.read() 

open(filename, 'w').write(new_txt)

with 语句使事情变得更短,因为我不必显式打开和关闭文件。

还有其他想法吗?

【问题讨论】:

    标签: python coding-style


    【解决方案1】:

    我使用generator expressions 的丑陋(但如问题中所述短)解决方案;

    # Some setup first
    file('test.txt', 'w').write('\n'.join('%05d' % i for i in range(100)))
    
    
    # This is the filter function
    def f(i):
        return i % 3
    
    
    # This is the main part 
    file('test2.txt', 'w').write('\n'.join(str(f(int(l))) for l in file('test.txt', 'r').readlines()))
    
    
    # And a wrapper for sanity
    def filter_file(infile, outfile, filter_function)
        outfile.write('\n'.join(filter_function(l) for l in infile.readlines()))
    

    【讨论】:

      【解决方案2】:

      其实使用fileinput更简单的方法是使用inplace参数:

      import fileinput
      for line in fileinput.input (filenameToProcess, inplace=1):
          process (line)
      

      如果您使用 inplace 参数,它会将标准输出重定向到您的文件,因此如果您进行打印,它将写回您的文件。

      此示例将行号添加到您的文件中:

      import fileinput
      
      for line in fileinput.input ("b.txt",inplace=1):
          print "%d: %s" % (fileinput.lineno(),line),
      

      【讨论】:

      • 非常好,感谢您指出这个选项。也可以使用 fileinput 中的 filelineno() 函数自动得到行号,不用自己计算。
      • 哦,你忘了打印后的逗号 - 代码添加了额外的换行符:-)
      • 感谢您了解这一点——我已经更改了示例。
      【解决方案3】:

      如果您在中间崩溃,则不会eat your data

      from twisted.python.filepath import FilePath
      p = FilePath(filename)
      p.setContent(process(p.getContent()))
      

      【讨论】:

        【解决方案4】:

        如果您正在寻找相当于“perl -pi”的python,这里有一个非常好的:

        导入文件输入 对于 fileinput.input() 中的行: # 工艺线

        请参阅http://www.python.org/doc/2.5.2/lib/module-fileinput.html 了解更多信息。

        通过这种方式,您将在管道中使用您的 python 脚本来创建新文件:

        $ myscript.py infile.txt > outfile.txt

        【讨论】:

        • 它并没有真正帮助我,因为我想写回同一个文件。对于同一个文件,重定向不会以这种方式工作
        【解决方案5】:

        我会以不同的方式追求优雅:将您的文件读取和过滤操作实现为生成器,您将编写更多代码行,但它会更灵活、可维护且性能更高。

        请参阅 David M. Beazley 的 Generator Tricks for Systems Programmers,这对于编写此类代码的人来说非常重要。

        【讨论】:

        • 很好的链接——谢谢!我有点担心调试管道的难度增加,但它的力量是不可否认的。
        • 测试驱动开发是你的朋友。
        【解决方案6】:

        这似乎有效:

        with open(filename, "r+") as f:
            new_txt = process(f.read())
            f.truncate(0)
            f.write(new_txt)
        

        【讨论】:

        • 只有在 f.truncate(0) 之后调用 f.seek(0) 时才有效,否则新文件以 11 个零字节开头(Linux 上的 Python 2.7.3)。
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2016-10-15
        • 2010-09-24
        • 1970-01-01
        • 2017-03-10
        • 1970-01-01
        相关资源
        最近更新 更多