I have a file containing python's object as string, then i open it and doing things like i showing:
>>> file = open('gods.txt')
>>> file.readlines()
["{'brahman': 'impersonal', 'wishnu': 'personal, immortal', 'brahma': 'personal, mortal'}\n"]
But then i have problem because there is no longer any lines:
>>> f.readlines()
[]
>>> f.readline(0)
''
Why it is heppening and how can i stay with access to file's lines?
There's only one line in that file, and you just read it. readlines returns a list of all the lines. If you want to re-read the file, you have to do file.seek(0)
Your position in the file has moved
f = open("/home/usr/stuff", "r")
f.tell()
# shows you're at the start of the file
l = f.readlines()
f.tell()
# now shows your file position is at the end of the file
readlines() gives you a list of contents of the file, and you can read that list over and over. It's good practice to close the file after reading it, and then use the contents you've got from the file. Don't keep trying to read the file contents over and over, you've already got it.
save the result to a variable or reopen the file?
lines = file.readlines()
You can store the lines list in a variable and then access it
whenever you want:
file = open('gods.txt')
# store the lines list in a variable
lines = file.readlines()
# then you can iterate the list whenever you want
for line in lines:
print line
Related
This question already has answers here:
Why can't I call read() twice on an open file?
(7 answers)
Closed 7 months ago.
I have a problem with iterating on a file. Here's what I type on the interpreter and the result:
>>> f = open('baby1990.html', 'rU')
>>> for line in f.readlines():
... print(line)
...
# ... all the lines from the file appear here ...
When I try to iterate on the same open file again I get nothing!
>>> for line in f.readlines():
... print(line)
...
>>>
There is no output at all. To solve this I have to close() the file then open it again for reading! Is that normal behavior?
Yes, that is normal behavior. You basically read to the end of the file the first time (you can sort of picture it as reading a tape), so you can't read any more from it unless you reset it, by either using f.seek(0) to reposition to the start of the file, or to close it and then open it again which will start from the beginning of the file.
If you prefer you can use the with syntax instead which will automatically close the file for you.
e.g.,
with open('baby1990.html', 'rU') as f:
for line in f:
print line
once this block is finished executing, the file is automatically closed for you, so you could execute this block repeatedly without explicitly closing the file yourself and read the file this way over again.
As the file object reads the file, it uses a pointer to keep track of where it is. If you read part of the file, then go back to it later it will pick up where you left off. If you read the whole file, and go back to the same file object, it will be like reading an empty file because the pointer is at the end of the file and there is nothing left to read. You can use file.tell() to see where in the file the pointer is and file.seek to set the pointer. For example:
>>> file = open('myfile.txt')
>>> file.tell()
0
>>> file.readline()
'one\n'
>>> file.tell()
4L
>>> file.readline()
'2\n'
>>> file.tell()
6L
>>> file.seek(4)
>>> file.readline()
'2\n'
Also, you should know that file.readlines() reads the whole file and stores it as a list. That's useful to know because you can replace:
for line in file.readlines():
#do stuff
file.seek(0)
for line in file.readlines():
#do more stuff
with:
lines = file.readlines()
for each_line in lines:
#do stuff
for each_line in lines:
#do more stuff
You can also iterate over a file, one line at a time, without holding the whole file in memory (this can be very useful for very large files) by doing:
for line in file:
#do stuff
The file object is a buffer. When you read from the buffer, that portion that you read is consumed (the read position is shifted forward). When you read through the entire file, the read position is at the end of the file (EOF), so it returns nothing because there is nothing left to read.
If you have to reset the read position on a file object for some reason, you can do:
f.seek(0)
Of course.
That is normal and sane behaviour.
Instead of closing and re-opening, you could rewind the file.
I have a txt file that contains names which are separated by lines but with some empty lines.
When I execute the following code, every second name gets ommitted in the output array.
Why is that?
def get_string_list(string_textfile):
list = []
file = open("names.txt", "r")
for line in file:
line = file.readline()[:-1]
list.append(line.lower())
return list
when you iterate the file
for line in file:
# you read line just now it exists
line = file.readline()
# uh oh you just read another line... you didnt do anything with the first one
dont mix iteration of a file with readline in general (in fact i think modern python versions will throw an error if you try to mix these two)
if all you want is a list of lines you can do any of the following
lines = list(file)
# or
lines = file.readlines()
you can get only non_empty lines and strip newlines as follows
lines_stripped = list(filter(None,(l.strip() for l in file)))
not super pythonic but its nice and terse and pretty clear what its doing
modify for statements like following:
for line in file:
list.append(line.strip().lower())
list = [name for name in list if name]
last line added to remove empty line.
I want to insert a line into file "original.txt" (the file contains about 200 lines). the line neds to be inserted two lines after a string is found in one of the existing lines. This is my code, I am using a couple of print options that show me that the line is being added to the list, in the spot I need, but the file "original.txt" is not being edited
with open("original.txt", "r+") as file:
lines = file.readlines() # makes file into a list of lines
print(lines) #test
for number, item in enumerate(lines):
if testStr in item:
i = number +2
print(i) #test
lines.insert(i, newLine)
print(lines) #test
break
file.close()
I am turning the lines in the text into a list, then I enumerate the lines as I look for the string, assigning the value of the line to i and adding 2 so that the new line is inserted two lines after, the print() fiction shows the line was added in the correct spot, but the text "original.txt" is not modified
You seem to misunderstand what your code is doing. Lets go line by line
with open("original.txt", "r+") as file: # open a file for reading
lines = file.readlines() # read the contents into a list of lines
print(lines) # print the whole file
for number, item in enumerate(lines): # iterate over lines
if testStr in item:
i = number +2
print(i) #test
lines.insert(i, newLine) # insert lines into the list
print(lines) #test
break # get out of the look
file.close() # not needed, with statement takes care of closing
You are not modifying the file. You read the file into a list of strings and modify the list. To modify the actual file you need to open it for writing and write the list back into it. Something like this at the end of the code might work
with open("modified.txt", "w") as f:
for line in lines: f.write(line)
You never modified the original text. Your codes reads the lines into local memory, one at a time. When you identify your trigger, you count two lines, and then insert the undefined value newLine into your local copy. At no point in your code did you modify the original file.
One way is to close the file and then rewrite it from your final value of lines. Do not modify the file while you're reading it -- it's good that you read it all in and then start processing.
Another way is to write to a new file as you go, then use a system command to replace the original file with your new version.
I open a file using a python programme.
file = open('test.txt', 'r')
Then I set a variable:
data = file.read()
And another one:
data2 = file.readlines()
The data variable should be a string and data2 a list. Printing data works fine, but when I try to print data2, I get an empty list. Why does it work like that? Why does setting data iterfere with data2?
When you open a file it returns a file pointer. This means that you can only read each line once. After you use read(), it reads the entire file, moving the file pointer to the end. Then when you use readlines() it returns an empty list because there are no lines past the end of the file.
You have consumed the iterator with file.read() so there is nothing left to consume when you call readlines, you would need to file.seek(0) before the call to readlines to reset the pointer to the start of the file.
with open('test.txt') as f: # with closes your files automatically
data = f.read()
f.seek(0) # reset file pointer
data2 = f.readlines()
It's not so much that setting data interferes with data2. Rather, it is calling file.read() interfering with file.readlines().
When you opened the file with file = open('test.txt', 'r'), the variable file is now a pointer to the file.
Thus, when you call file.read() or file.readlines(), it moves the pointer file.
file.read() moves the pointer to the end of the file, so there is no more like to read for file.readlines().
Even though you are assigning them to different variable, they ultimately depend on file. So by setting data, you modify file which interferes with your attempt to set data2.
Why don't you split the string instead of reading the file again.
file = open('test.txt', 'r')
data = file.read()
data2 = data.split('\n')
import os.path
os.path.exists('~/fileToExperiment.txt')
myfile = open('~/fileToExperiment.txt','r')
myfile.readlines()
for line in myfile:
print line
So I am trying to run this very simple python code but it doesnot output anything nor does it has any errors.
The filestoExperiment text is not empty.
Whats wrong here ? Could someone point out
By doing, myfile.readlines() you already read the entire file. Then, we you try to iterate over your file object, you already are at the end of the file.
A better practice is to do:
with open('~/fileToExperiment.txt','r') as myfile:
for line in myfile:
print line
myfile.readlines() will store the whole content of the file in memory. If you do not need the entire content at once, it is best to read line by line.
If you do need the entire content, you can use
with open('~/fileToExperiment.txt','r') as myfile:
content = myfile.read() ## or content = myfile.readlines()
Also note the use of the with statement, which is recommended when handling files (no need to close the file afterwards).
You didn't store the lines in a variable. So try this:
lines = myfile.readlines()
for line in lines:
print line
You can use either readlines() or looping file object to print or read the lines from file.
readlines() - returns the complete file as a "list of strings each separated by \n"
for example,
code:
print myfile.readlines()
output:
['Hello World\n', 'Welcome to Python\n', 'End of line\n']
Looping file object - You can loop over the file object for reading lines from a file. This is memory efficient, fast, and leads to simple code. For example,
code:
myfile = open('newfile.txt', 'r')
for line in myfile:
print line
output:
Hello World
Welcome to Python
End of line