0

Is there a faster way to replace the third line of file by another one without using cell ?

I've used this code but it slows my programs, especially that my txt file is composed by more than 1000 lines

% Read txt into cell A
    fid7 = fopen([handles.filenameproba],'r');
    i = 1;
    tline = fgetl(fid7);
    A{i} = tline;
    while ischar(tline)
        i = i+1;
        tline = fgetl(fid7);
        A{i} = tline;
    end
    fclose(fid7);
    % Change cell A
    newval =...

    A{3} = sprintf('StartExperiment:%s',num2str(newval);
    % Write cell A into txt
    fid7 = fopen([handles.filenameproba], 'w');
    for i = 1:numel(A)
        if A{i+1} == -1
            fprintf(fid7,'%s', A{i});
            break
        else
            fprintf(fid7,'%s\n', A{i});
        end
    end
  fclose(fid7);

Thanks !

ranell
  • 683
  • 13
  • 29
  • I think reading the file using textscan with the newline being the delimiter would be a lot faster than fgetl http://stackoverflow.com/questions/9440592/fastest-matlab-file-reading you could also consider doing that with python should be fairly easy – mhmsa Jun 02 '14 at 19:42

2 Answers2

0

If performance is your primary concern, try this importdata approach to see if it's any faster -

f=importdata(handles.filenameproba,'')
f(3)={sprintf('StartExperiment:%s',num2str(newval))}

%%// Save the modified text file
fid1 = fopen(handles.filenameproba,'w');
for k = 1:numel(f)
    fprintf(fid1,'%s\n',f{k});
end
fclose(fid1);
Divakar
  • 218,885
  • 19
  • 262
  • 358
0

Cells are not your problem. Your problem is reading and writing one line at a time. Additionally, you are re-sizing your cell array at every iteration.

For the following problem, I created a test file with 10000 lines in it.

fileId = fopen('test.txt', 'w');
for i = 1:10000
    fprintf(fileId, 'This is the %dth line.\n', i);
end
fclose(fileId);

I'm calling your method ranellMethod.

>> timeit(@ranellMethod)

ans =

    0.5160

A better way to do it is to limit the number of read/write operations you have to do. Assuming your file is small enough, you can read the entire contents into memory at once. Perform your operations, and write everything at once.

function entireFileMethod()
    fileName = 'test.txt';
    fileId = fopen(fileName, 'r');
    try
        text = fread(fileId, '*char')'; %'
    catch Me
        fclose(fileId);
        Me.rethrow();
    end
    fclose(fileId);
    newLineInds = find(text == char(10));
    newLine = sprintf('This is the new line. %1.*f', randi(10), rand);
    newText = [text(1:newLineInds(2)), newLine, text(newLineInds(3):end)];
    fileId = fopen(fileName, 'w');
    try
        fprintf(fileId, '%s', newText);
    catch Me
        fclose(fileId);
        Me.rethrow();
    end
    fclose(fileId);
end

This function has one read operation, and one write operation:

>> timeit(@entireFileMethod)

ans =

    0.0043

See Fastest Matlab file reading? for more detailed information about file IO in MATLAB

Community
  • 1
  • 1
hoogamaphone
  • 1,092
  • 10
  • 20