I want to replace string in a line which contain patternB, something like this:
from:
some lines
line contain patternA
some lines
line contain patternB
more lines
to:
some lines
line contain patternA
some lines
line contain patternB xx oo
more lines
I have code like this:
inputfile = open("d:\myfile.abc", "r")
outputfile = open("d:\myfile_renew.abc", "w")
obj = "yaya"
dummy = ""
item = []
for line in inputfile:
dummy += line
if line.find("patternA") != -1:
for line in inputfile:
dummy += line
if line.find("patternB") != -1:
item = line.split()
dummy += item[0] + " xx " + item[-1] + "\n"
break
outputfile.write(dummy)
It do not replace the line contain "patternB" as expected, but add an new line below it like :
some lines
line contain patternA
some lines
line contain patternB
line contain patternB xx oo
more lines
What can I do with my code?
Of course it is, since you append line to dummy in the beginning of the for loop and then the modified version again in the "if" statement. Also why check for Pattern A if you treat is as you treat everything else?
inputfile = open("d:\myfile.abc", "r")
outputfile = open("d:\myfile_renew.abc", "w")
obj = "yaya"
dummy = ""
item = []
for line in inputfile:
if line.find("patternB") != -1:
item = line.split()
dummy += item[0] + " xx " + item[-1] + "\n"
else:
dummy += line
outputfile.write(dummy)
The simplest will be:
1. Read all File into string
2. Call string.replace
3. Dump string to file
If you want to keep line by line iterator
(for a big file)
for line in inputfile:
if line.find("patternB") != -1:
dummy = line.replace('patternB', 'patternB xx oo')
outputfile.write(dummy)
else:
outputfile.write(line)
This is slower than other responses, but enables big file processing.
This should work
import os
def replace():
f1 = open("d:\myfile.abc","r")
f2 = open("d:\myfile_renew.abc","w")
ow = raw_input("Enter word you wish to replace:")
nw = raw_input("Enter new word:")
for line in f1:
templ = line.split()
for i in templ:
if i==ow:
f2.write(nw)
else:
f2.write(i)
f2.write('\n')
f1.close()
f2.close()
os.remove("d:\myfile.abc")
os.rename("d:\myfile_renew.abc","d:\myfile.abc")
replace()
You can use str.replace:
s = '''some lines
line contain patternA
some lines
line contain patternB
more lines'''
print(s.replace('patternB', 'patternB xx oo'))
Related
I have a txt file named a.txt. In this file a has a string per line. I want to append these strings line by line to the keyword = {} dict and run my double_letter function for each line of string. How can I do it?
my double_letter function:
keyword = {}
def double_letter():
print("\nDouble Letter:\n")
idx = random.randint(0, len(keyword) - 1)
keyword = keyword[:idx] + keyword[idx] + keyword[idx:]
print(keyword)
You can open, read and print the contents of a txt file as follows:
f = open("a.txt", "r")
for line in f:
print(line)
You can add in your function for each run through the for loop, i.e. calling it during each line of the text:
f = open("a.txt", "r")
for line in f:
print(line)
double_letter()
IIUC
Code
import random
def double_letter(line):
'''
Repeats random letter in line
'''
if line:
idx = random.randint(0, len(line) - 1)
return line[:idx] + line[idx] + line[idx:]
else:
return line # does nothing with blank lines
with open("a.txt", "r") as f: # with preferred with open file
keyword = {} # setup results dictionary
for line in f:
line = line.rstrip() # remove the '\n' at the end of each line
keyword[line] = double_letter(line) # add line with it's repeat to dictionary
print(keyword)
File a.txt
Welcome
To
Stackoverflow
Output
{'Welcome': 'Welcomee', 'To': 'Too', 'Stackoverflow': 'Stackoverfloow'}
I am trying to make a parser for my text adventure. I used a text file called test.txt.
I keep getting IndexError: string index out of range. How can I fix this?
parser.py
def parse(file):
data = {}
with open(file, "r") as f:
lines = f.readlines()
f.close()
for line in lines:
line = line.strip()
if line[0] == "#":
name = line[1:]
name = name.replace("\n", "")
data[name] = {}
if line[0] == "-":
prop = line.split(":")
prop_name = prop[0].replace("-", "")
prop_name = prop_name.replace("\n", "")
prop_desc = prop[1][1:]
prop_desc = prop_desc.replace("\n", "")
data[name][prop_name] = prop_desc
return data
print(parse("test.txt"))
test.txt
#hello
-desc: Hello World! Lorem ipsum
-north: world
#world
-desc: World Hello! blah
-south: hello
You're stripping the newlines (line = line.strip()), so if a line is empty, there is just an empty string and line[0] is out of range.
You should test if the line is truthy:
if line and line[0] == "-":
Or, better, in the beginning of the loop, skip blank lines:
for line in lines:
if line == '\n':
continue
# rest of code
Since there is many "\n" in your text, you should ignore them in file reading.
try this:
with open(file, "r") as f:
lines = f.readline().splitlines()
f.close()
I wrote a function that is supposed to add the words from a .txt to a list but it is supposed to ignore empty lines, how ever my function outputs ['',] at an empty line.
def words(filename):
word = []
file = open(filename)
for line in file:
word.append(line.strip())
return word
How can i fix this thanks
what about a simple if test?
def words(filename):
word = []
file = open(filename)
for line in file:
if line.strip() != ' ':
word.append(line.strip())
return word
EDIT: I forgot the .strip() after line
Besides, you could also use if line.strip():
Last, if you want to get a list of words but have several words per line, you need to split them. Assuming your separator is ' ':
def words(filename):
word = []
file = open(filename)
for line in file:
if line.strip() != ' ':
word.extend(line.strip().split())
return word
You can fix this like that:
def words(filename):
word = []
file = open(filename)
for line in file:
if not line.strip():
word.append(line)
return word
Your problem is that you're adding line.strip(), but what happens if line is actually an empty string? Look:
In [1]: line = ''
In [2]: line.strip()
Out[2]: ''
''.strip() returns an empty string.
You need to test for an empty line and skip the append in that case.
def words(filename):
word = []
file = open(filename)
for line in file:
line=line.strip()
if len(line):
word.append(line)
return word
I want to read the above file foo.txt and read only UDE from the first line and store it in a variable then Unspecified from the second line and store it in a variable and so on.
should I use read or readlines ? should I use regex for this ??
My below program is reading the entire line. how to read the specific word in the line ?
fo = open("foo.txt", "r+")
line = fo.readline()
left, right = line.split(':')
result = right.strip()
File_Info_Domain = result
print File_Info_Domain
line = fo.readline()
left, right = line.split(':')
result = right.strip()
File_Info_Intention = result
print File_Info_Intention
line = fo.readline()
left, right = line.split(':')
result = right.strip()
File_Info_NLU_Result = result
print File_Info_NLU_Result
fo.close()
You can use readline() (without s in name) to read line on-by-one, and then you can use split(':') to get value from line.
fo = open("foo.txt", "r+")
# read first line
line = fo.readline()
# split line only on first ':'
elements = line.split(':', 1)
if len(elements) < 2:
print("there is no ':' or there is no value after ':' ")
else:
# remove spaces and "\n"
result = elements[1].strip()
print(result)
#
# time for second line
#
# read second line
line = fo.readline()
# split line only on first ':'
elements = line.split(':', 1)
if len(elements) < 2:
print("there is no ':' or there is no value after ':' ")
else:
# remove spaces and "\n"
result = elements[1].strip()
print(result)
# close
fo.close()
While you can use #furas response or regex, I would recommend you to use a config file to do this, instead of a plain txt. So your config file would look like:
[settings]
Domain=UDE
Intention=Unspecified
nlu_slot_details={"Location": {"literal": "18 Slash 6/2015"}, "Search-phrase": {"literal": "18 slash 6/2015"}
And in your python code:
import configparser
config = configparser.RawConfigParser()
config.read("foo.cfg")
domain = config.get('settings', 'Domain')
intention = config.get('settings', 'Intention')
nlu_slot_details = config.get('settings', 'nlu_slot_details')
I'm adding some new bits to one of the lines in a text file and then writing it along with the rest of the lines in the file to a new file. Referring to the 2nd if statement in the while loop, I want that to be all on the same line:
path = raw_input("Enter the name of the destination folder: ")
source_file = open("parameters")
lnum=1
for line in source_file:
nums = line.split()
if (lnum==10):
mTot = float(nums[0])
if (lnum==11):
qinit = float(nums[0])
if (lnum==12):
qfinal = float(nums[0])
if (lnum==13):
qgrowth = float(nums[0])
if (lnum==14):
K = float(nums[0])
lnum = lnum+1
q = qinit
m1 = mTot/(1+qinit)
m2 = (mTot*qinit)/(1+qinit)
taua = (1/3.7)*(mTot**(-4.0/3.0))
taue = taua/K
i = 1
infname = 'parameters'
while (q <= qfinal):
outfname = path+'/'+str(i)
oldfile = open(infname)
lnum=1
for line in oldfile:
if (lnum==17):
line = "{0:.2e}".format(m1)+' '+line
if (lnum==18):
line = "{0:.2e}".format(m2)+' '+line+' '+"{0:.2e}".format(taua)+' '+" {0:.2e}".format(taue)
newfile = open(outfname,'a')
newfile.write(line)
lnum=lnum+1
oldfile.close()
newfile.close()
i=i+1
q = q + q*(qgrowth)
m1 = mTot/(1+q)
m2 = (mTot*q)/(1+q)
but taua and taue are being written on the line below the rest of it. What am I missing here?
That is because line still contains the trailing newline, and when you concatenate it you are also including the newline.
Insert a
line = line.strip()
right after the if (lnum == 19): but before you put the longer line together to get rid of the newline.
Note that write will not add a newline automatically, so you'll want to add a trailing newline of your own.
UPDATE:
This is untested, but I think unless I messed up, you could just use this instead of your longer line:
line = line.strip()
line = "{0:.2e} {} {0:.2e} {0:.2e}\n".format(x, line, y, z)
If you use line = rstrip(line) on line before you change the line then it will trim the new line (as well as any whitespace).