I have the following code that pulls a list from a txt file and then prints one line at a time. The problem I am having is that I want the code to remove that line from the txt file after it has printed it.
I have tried using a few different methods I found online but had no success on maiking it work.
Would any have any idea's on how to achive this?
import time
from time import sleep
import random
my_file=open('testlist.txt','r')
file_lines=my_file.readlines()
my_file.close()
for line in file_lines:
try:
sep = line.split(":")
select_list = ["test " sep[0] "? " sep[1], "test " sep[0] "! " sep[1], "test " sep[0] "? " sep[1]]
print(random.choice(select_list))
sleep(1)
except Exception as e:
print(e)
Basically after the "print(random.choice(select_list))", we would want to delete "line" from "testlist.txt".
CodePudding user response:
I create two .txt file, skip the unwanted line with continue
with open("/home/ts/Desktop/1.txt", "r ") as f_1:
with open("/home/ts/Desktop/2.txt", "r ") as f_2:
for i in f_1:
if "3" in i:
continue
f_2.write(i)
CodePudding user response:
I would give you example but better try to follow this guide there is various ways , first issue is opening the file with 'r' mode
CodePudding user response:
Let's go through some logic and see how to achieve the results you are expecting.
Humanly / Intuitively, the actions are
1. Read files line-by-line to memory
my_file=open('testlist.txt','r')
file_lines=my_file.readlines()
my_file.close()
It would be a better practice to consider using with
context managers (it will automatically help you close the file one you are out of the indentation from the with
scope, i.e.
with open('testlist.txt','r') as my_file:
file_lines = my_file.readlines()
2. For each line that is read, (a) split it by :
character, (b) perform a few string operations and (c) randomly select one of the output from (2b), i.e
for line in file_lines:
sep = line.split(":")
select_list = ["test " sep[0] "? " sep[1], "test " sep[0] "! " sep[1], "test " sep[0] "? " sep[1]]
print(random.choice(select_list))
2b. Now, lets take a look at (2b) and see what we are trying to achieve, i.e.
select_list = ["test " sep[0] "? " sep[1], "test " sep[0] "! " sep[1], "test " sep[0] "? " sep[1]]
We produce 3 items in the select_list
, where it seems the "test " sep[0] "? " sep[1]
has 2 occurence and the "test " sep[0] "! " sep[1]
is included once.
"test " sep[0] "? " sep[1]
"test " sep[0] "! " sep[1]
"test " sep[0] "? " sep[1]
in any case, the select_list = [ ... ]
is a valid line of code.
2c. Regarding the print(random.choice(select_list))
line, it doesn't affect any variables and it's just randomly choosing an item from the select_list
Going back to original question,
I want the code to remove that line from the txt file after it has printed it.
Q: Would this mean removing the line from the original file_lines
in open('testlist.txt','r')
?
A: If so, then it would be removing all lines from the original testlist.txt
, because if everything would checks out for step 2b and 2c (in the try
part of the code).
But if step 2b or 2c throws an error and get caught in the except
, then it would be a line that you won't want to throw out (as per your original question).
In that case, it looks like what you want to get eventually is a list of lines that falls into the except
scope of the code.
If so, then you would be looking at something like this:
# Reading the original file.
with open('testlist.txt','r') as my_file:
# Opening a file to write the lines that falls into the exception
with open('testlist-exceptions.txt', 'w') as fout:
# Iterate through the original file line by line.
for line in my_file:
# Step 2a.
sep = line.split(":")
# Supposedly step 2b, but since this is the only
# point of the code that can throw an exception
# most probably because there's no sep[1],
# you should instead check the length of the sep variable.
if len(sep) < 2: # i.e. does not have sep[1].
# Write to file.
fout.write(line)
else: # Otherwise, perform the step 2b.
select_list = ["test " sep[0] "? " sep[1], "test " sep[0] "! " sep[1], "test " sep[0] "? " sep[1]]
print(random.choice(select_list))
Now the new logic is a lot simpler than the intuition based logic you have in the original code but achieves the same output that you are expecting.
The new logic is as such:
- Open the original file for reading, open another file to write the file that I expect
- Read the file line by line
- Split the file by
:
- Check if it allows the string operation to join the
sep[0]
andsep[1]
- if yes, perform the string operation to create
select_list
and choose one of the item inselect_list
to print to console - if no, print out that line to the output file.
- if yes, perform the string operation to create
If for some reason, you really want to work with the file in place with Python, then take a look at Is it possible to modify lines in a file in-place?
And if you really need to reduce memory footprint and want something that can edit lines of the file in-place, then you would have to dig a little into file seek
function https://docs.python.org/3/tutorial/inputoutput.html#methods-of-file-objects
Some unsolicited Python suggestions (hope this helps)
When you need to delete something from file, if disk space allows, don't delete it, create another file with the expected output with the deleted lines.
Whenever possible, try to treat files that you want to read as immutable, and less like Perl-style in-place files that allows edits
It's tempting to do try-excepts when you just want something to work, but catch-all excepts are hard to debug and normally shows that the logic of the steps can be better. https://docs.python.org/3/tutorial/errors.html#handling-exceptions