Editing a single line in a large text file

Therefore, I need to write a set of 4 integers, the values ​​of which differ for every second part of the day. i.e:.

#Here the values are initialized to the same value, however they will change as samples are taken data = [[.25 for numData in range(4)] for numSecs in range(86400)] 

Now it’s obvious that a two-dimensional array (gah of its python, LIST), whose first length is 86400, is quite impractical. Instead, I want to create a text file with 86400 lines formatted as such:

 numSec data0 data1 data2 data3 0 .25 .25 .25 .25 1 .25 .25 .25 .25 2 .25 .25 .25 .25 ... 

And since the samples are taken, I want to be able to edit this file, no, I want to be able to edit the line of the file, numSec = the second sample was taken. For example, a sample taken in numSec = 2 (2 seconds after midnight) will force my program to edit the file so that:

 0 .25 .25 .25 .25 1 .25 .25 .25 .25 2 .70 .10 .10 .10 ... 

It seems simple enough, I even read a bunch of posts that demonstrated how to rewrite a single in a text file. The problem is that they all require you to read the entire file. I do not want my program to read 86,400 lines every second.

Thus, we come to my question: can I read one line in a text file, edit it and write to a file without reading the entire file every time I need to make changes?

PS I should note that I am running Ubuntu 12.04 (Precise), and this is for use in the ROS node

PPS This program will work for an arbitrary number of days, so that every "second" information can be read and rewritten many times. Another reason I would like to use the file is that I need to turn off the system, I would like to save the distributions the next time it starts.

+6
source share
4 answers

You may need to slightly modify this value and assume that all lines are the same length. To do this, I had to move the first column to a fixed width. But if you do not want to fill in, you should be able to count the number 1,2,3,4, ... digits to a specific line.

 data = [[.25 for numData in range(4)] for numSecs in range(86400)] length_line=0 def write_line(f, sec, data): line="{:6d}".format(sec) + " " +" ".join( ["{:.2f}".format(dd) for dd in data])+"\n" f.write(line) return len(line) with open('output', 'w') as of: for i,d in enumerate(data): length_line=write_line(of, i, d) with open('output', 'rb+') as of: # modify the 2nd line: n = 2 of.seek(n*length_line) write_line(of, n, [0.10,0.10,0.10,0.10]) # modify the 10th line: n = 10 of.seek(n*length_line) write_line(of, n, [0.10,0.10,0.10,0.10]) 
+3
source

If the lines have different lengths, then everything after the changed line will be in the wrong position, and you will have to rewrite all these lines. If all lines have the same length, then you can seek() and write() to get new data by calculating the line offset in the file. See Python File Objects for more details.

+2
source

I am not sure if it is useful to store 345600 (86400 * 4) times 0.25. Just save the default value in the first line. Then add one line at a time. If timestamps do not come just to put them as they are, and after the day is over, sort the contents of the file once and fill in the missing default timestamps. Example:

 default: 0.25 2 .70 .10 .10 .10 3 .80 .20 .20 .20 1 .50 .30 .30 .30 5 .40 .30 .30 .30 

Process this file later to get the following:

 1 .50 .30 .30 .30 2 .70 .10 .10 .10 3 .80 .20 .20 .20 4 .25 .25 .25 .25 5 .40 .30 .30 .30 
0
source

If I were you, I would use a sqlite database to store records. The key will be the second of the observations, and each row will consist of 4 values. Updating and editing will be much more efficient.

0
source

Source: https://habr.com/ru/post/947001/


All Articles