python:打开文件,编辑一行,另存为同一文件

python: Open file, edit one line, save it as the same file

提问人:straumle 提问时间:5/11/2015 最后编辑:straumle 更新时间:5/11/2015 访问量:30260

问:

我想打开一个文件,搜索一个特定的单词,更改该单词并再次保存文件。听起来很容易 - 但我就是无法让它工作......我知道我必须覆盖整个文件,但只能更改这一个单词!

我的代码:

f = open('./myfile', 'r')
linelist = f.readlines()
f.close

for line in linelist:
    i =0;
    if 'word' in line:
        for number in arange(0,1,0.1)):
            myNumber = 2 - number
            myNumberasString = str(myNumber)

            myChangedLine = line.replace('word', myNumberasString)


            f2 = open('./myfile', 'w')
            f2.write(line)
            f2.close

            #here I have to do some stuff with these files so there is a reason
            #why everything is in this for loop. And I know that it will
            #overwrite the file every loop and that is good so. I want that :)

如果我这样做,“新”myfile 文件仅包含更改的行。但是我想要整个文件,其中有更改的行......谁能帮我?

编辑*****

我修好了!我只是把循环转过来,现在它像这样完美地工作:

f=open('myfile','r')
text = f.readlines()
f.close()

i =0;
for number in arange(0,1,0.1):
    fw=open('mynewfile', 'w')

    myNumber = 2 - number
    myNumberasString = str(myNumber)
    for line in text:

        if 'word' in line:
            line = line.replace('word', myNumberasString)

        fw.write(line)
    fw.close()
    #do my stuff here where I need all these input files
Python IO

评论

2赞 jonrsharpe 5/11/2015
您正在使用 mode 截断整个文件,并且只写出一个;你期待什么?'w'line
1赞 straumle 5/11/2015
好吧,如果你这样写,我不可能期待不同的东西。但这是编写我发现的文件的唯一解决方案......这就是我发布这个问题的原因。那我该怎么做呢?
2赞 Max Spencer 5/11/2015
@Cheng OP 想要就地替换该行,而不一定是附加。
0赞 straumle 5/11/2015
@Cheng:但我不想把它添加到文档的末尾。台词必须按照它们的顺序抵抗,只有这一个词必须改变......
0赞 Max Spencer 5/11/2015
@straumle:你想用内部循环做什么,你只是在第一次迭代中用“2”替换“word”,然后据我所知不做任何其他事情?for

答:

1赞 ODiogoSilva 5/11/2015 #1

当前代码存在三个问题。首先,在开始循环之前创建文件句柄,否则将在每次迭代中覆盖文件。第三,您正在 中编写一行未修改的行。我猜你的意思是?第三,您应该添加一个语句,将未修改的行写入文件。所以:f2f2.write(line)f2.write(myChangedLine)else

f = open('./myfile', 'r')
linelist = f.readlines()
f.close
f2 = open('./myfile', 'w')

for line in linelist:
    i =0;
    if 'word' in line:
        for number in arange(0,1,0.1)):
            myNumber = 2 - number
            myNumberasString = str(myNumber)

            myChangedLine = line.replace('word', myNumberasString)

            f2.write(myChangedLine)
    else:
        f2.write(line)

f2.close()

评论

0赞 straumle 5/11/2015
您好,感谢您的回答。我想在每次迭代中覆盖文件:)如果我这样做,它只会在文本文件的末尾添加一行。但这不是我想要的。我想替换现有文件中的单词,以便它看起来完全相同,除了这个单词......
5赞 Padraic Cunningham 5/11/2015 #2

使用 fileinput 传入要替换的任何内容:

import  fileinput
for line in fileinput.input("in.txt",inplace=True):
    print(line.replace("whatever","foo"),end="")

你似乎没有在循环中做任何特别的事情,而这些事情不能在循环外首先计算,所以创建你想用它替换单词的字符串,并传递它来替换。

inplace=True将表示原始文件已更改。如果要验证一切正常,请删除第一次运行的输出,您将实际看到替换的输出,而不是写入文件的行。inplace=True

如果要写入临时文件,可以将 NamedTemporaryFileshutil.move 一起使用:

from tempfile import NamedTemporaryFile
from shutil import move

with open("in.txt") as f, NamedTemporaryFile(dir=".",delete=False) as out:
    for line in f:
        out.write(line.replace("whatever","foo"))

move("in.txt",out.name)

您可能会遇到的一个问题是将子字符串与替换匹配,因此,如果您知道该单词总是在句子中间被空格包围,则可以添加它,但如果没有,则需要拆分并检查每个单词。

from tempfile import NamedTemporaryFile
from shutil import move
from string import punctuation
with open("in.txt") as f, NamedTemporaryFile(dir=".",delete=False) as out:
    for line in f:
        out.write(" ".join(word if word.strip(punctuation) != "whatever" else "foo" 
                 for word in line.split()))

评论

1赞 straumle 5/11/2015
嗯。。。那也行不通。然后它只是用这一行覆盖整个文档......
0赞 Padraic Cunningham 5/11/2015
@straumle,发生这种情况的唯一方法是,如果您要替换的单词是您的整个文件
1赞 Blixt 5/11/2015
重要的是要知道,将该选项设置为“打开”将暂时接管脚本的当前电流,这可能会也可能不会起作用,具体取决于您的用例。使用该函数读取/写入文件可能更有意义,除非这只是一个简单的实用程序脚本。inplaceFileInputstdoutopen
0赞 Padraic Cunningham 5/11/2015
这仅替换为 if 出现在行中,如果行中没有,则原始行按原样编写。whateverfoowhateverwhatever
7赞 Max Spencer 5/11/2015 #3

你只需要边走边写出所有其他行。正如我在评论中所说,我不知道你真正想用你的替换做什么,但这里有一个稍微简化的版本,我们只是用“new”替换所有出现的“word”:

f = open('./myfile', 'r')
linelist = f.readlines()
f.close

# Re-open file here
f2 = open('./myfile', 'w')
for line in linelist:
    line = line.replace('word', 'new')
    f2.write(line)
f2.close()

或者使用上下文:

with open('./myfile', 'r') as f:
    lines = f.readlines()

with open('./myfile', 'w') as f:
    for line in lines:
        line = line.replace('word', 'new')
        f.write(line)

评论

0赞 straumle 5/11/2015
嗨,麦克斯。好的,但这也行不通。它只是用新行替换整个文档。但是我只想替换该行,并且文件的所有其他行必须保持不变......
0赞 Max Spencer 5/11/2015
我已经测试过了,它似乎按预期工作。如果我创建一个包含多行的文件,其中一些包含字符串“word”,那么在运行上述任一程序后,该文件仍然包含相同数量的行,只是所有出现的“word”都更改为“new”。