如何替换文件中的字符串?

时间:2017-06-04 00:10:07

标签: python

我在两个相似的文件中有两个数字。有一个new.txtoriginal.txt。除了数字之外,它们都有相同的字符串。 new.txt有一个字符串boothNumber="3"original.txt有一个字符串boothNumber="1"

我希望能够阅读new.txt,从中选择数字3并替换original.txt中的数字1。

有什么建议吗?这是我正在尝试的。

import re  # used to replace string
import sys # some of these are use for other code in my program

def readconfig():
    with open("new.text") as f:
        with open("original.txt", "w") as f1:
            for line in f:
                match = re.search(r'(?<=boothNumber=")\d+', line)
                for line in f1:
                    pattern = re.search(r'(?<=boothNumber=")\d+', line)
                    if re.search(pattern, line):
                        sys.stdout.write(re.sub(pattern, match, line))

当我运行它时,我的original.txt完全清除了任何文本。 我做了一次追溯,我得到了这个:

in readconfig
for line in f1:
io.UnsupportedOperationo: not readable

更新

我试过了:

def readconfig(original_txt_path="original.txt", 
               new_txt_path="new.txt"):
    with open(new_txt_path) as f:
        for line in f:
            if not ('boothNumber=') in line:
                continue
            booth_number = int(line.replace('boothNumber=', ''))
            # do we need check if there are more than one 'boothNumber=...' line?
            break
    with open(original_txt_path) as f1:
        modified_lines = [line.startswith('boothNumber=') if not line
                          else 'boothNumber={}'.format(booth_number)  
                          for line in f1]
    with open(original_txt_path, mode='w') as f1:
        f1.writelines(modified_lines)

我得到错误:

booth_number = int(line.replace('boothNumber=', ''))
ValueError: invalid literal for int() with base 10: '
(workstationID="1" "1" window=1= area="" extra parts of the line here)\n

在workstationID =“1”之后的“1”是boothNumber =“”通常会去的地方。当我打开original.txt时,我发现它实际上没有改变任何东西。

更新3

这是我的完整代码。请注意,文件名已更改,但我仍在尝试执行相同的操作。这是我的另一个想法或修改,但仍然无效:

import os
import shutil
import fileinput
import re  # used to replace string
import sys # prevents extra lines being inputed in config
           # example: sys.stdout.write


def convertconfig(pattern):                        
    source = "template.config"
    with fileinput.FileInput(source, inplace=True, backup='.bak') as file:
        for line in file:
            match = r'(?<=boothNumber=")\d+'
            sys.stdout.write(re.sub(match, pattern, line))


def readconfig():
    source = "bingo.config"
    pattern = r'(?<=boothNumber=")\d+'  # !!!!!!!!!! This probably needs fixed
    with fileinput.FileInput(source, inplace=True, backup='.bak') as file:
        for line in file:
            if re.search(pattern, line):
                fileinput.close()
                convertconfig(pattern)

def copyfrom(servername):

    source = r'//' + servername + '/c$/remotedirectory'
    dest = r"C:/myprogram"
    file = "bingo.config"
    try:
        shutil.copyfile(os.path.join(source, file), os.path.join(dest, file))

    except:
        print ("Error")

    readconfig()


# begin here
os.system('cls' if os.name == 'nt' else 'clear')
array = []
with open("serverlist.txt", "r") as f:
    for servername in f:

        copyfrom(servername.strip())

bingo.config是我的新文件 template.config是我原来的

它正在使用文字字符串“r”(?&lt; = boothNumber =“)\ d +'”

替换template.config中的数字

所以template.config最终看起来像

boothNumber="r'(?<=boothNumber=")\d+'"

而不是

boothNumber="2"

1 个答案:

答案 0 :(得分:2)

要查找boothNumber值,我们可以使用下一个正则表达式(使用regex101检查)

(?<=\sboothNumber=\")(\d+)(?=\")

这样的事情应该有效

import re
import sys # some of these are use for other code in my program

BOOTH_NUMBER_RE = re.compile('(?<=\sboothNumber=\")(\d+)(?=\")')
search_booth_number = BOOTH_NUMBER_RE.search
replace_booth_number = BOOTH_NUMBER_RE.sub


def readconfig(original_txt_path="original.txt", 
               new_txt_path="new.txt"):
    with open(new_txt_path) as f:
        for line in f:
            search_res = search_booth_number(line)
            if search_res is None:
                continue
            booth_number = int(search_res.group(0))
            # do we need check if there are more than one 'boothNumber=...' line?
            break
        else:
            # no 'boothNumber=...' line was found, so next lines will fail,
            # maybe we should raise exception like
            # raise Exception('no line starting with "boothNumber" was found')
            # or assign some default value
            # booth_number = -1
            # or just return?
            return

    with open(original_txt_path) as f:
        modified_lines = []
        for line in f:
            search_res = search_booth_number(line)
            if search_res is not None:
                line = replace_booth_number(str(booth_number), line)
            modified_lines.append(line)
    with open(original_txt_path, mode='w') as f:
        f.writelines(modified_lines)

测试

# Preparation
with open('new.txt', mode='w') as f:
    f.write('some\n')
    f.write('<jack Fill workstationID="1" boothNumber="56565" window="17" Code="" area="" section="" location="" touchScreen="False" secureWorkstation="false">')

with open('original.txt', mode='w') as f:
    f.write('other\n')
    f.write('<jack Fill workstationID="1" boothNumber="23" window="17" Code="" area="" section="" location="" touchScreen="False" secureWorkstation="false">')

# Invocation
readconfig()

# Checking output
with open('original.txt') as f:
    for line in f:
        # stripping newline character
        print(line.rstrip('\n'))

给出

other
<jack Fill workstationID="1" boothNumber="56565" window="17" Code="" area="" section="" location="" touchScreen="False" secureWorkstation="false">