how to change multiple items in a text file?

2 views (last 30 days)
hello
i have a text file with name of bp. u see many 'TSTEP' in this file. there are other written text just below them like: '1*100'. now i want to find these 'TSTEP's and make changes on the text below them (just changing the number before the asterisk). for example '1*100' is going to be '2.5*100' or any other number can be replaced. i use this code when i have one 'TSTEP' in file. ut it doesnt work for the cases when there are more than one of it. the number of TSTEPs may differ from file to file. is it possible to do that?
thanks in advance
clc;
fid=fopen('bp.txt','r');
c=textscan(fid,'%s','delimiter','\n','Whitespace','','CommentStyle','1','CollectOutput',0);
fclose(fid);
c=string(c{:})
iz=find(contains(c,"TSTEP"));
d1=['2.5','*',extractAfter(c{iz+1},'*')];
d2=replace(c,c{iz+1},d1);
fid = fopen('bp.txt','w');
for j= 1:length(d2)
fprintf(fid, '%s\n', char(d2{j}));
end
fclose(fid);

Accepted Answer

Stephen23
Stephen23 on 3 May 2019
Edited: Stephen23 on 7 May 2019
EDIT: much faster:
rpl = '2.5'; % the new value (you can generate this using NUM2STR).
str = fileread('bp.txt');
str = strtrim(regexp(str,'\n','split'));
idx = 1+find(strcmpi(str,'TSTEP'));
str(idx) = regexprep(str(idx),'^[^*]+',rpl);
fid = fopen('pb_new.txt','wt');
fprintf(fid,'%s\n',str{:});
fclose(fid);
ORIGINAL (SLOW): With a simple regular expression and regexprep:
rpl = '2.5'; % the new value (you can generate this using NUM2STR).
rgx = '(?<=\s+TSTEP\s+)\d+(?=\*100)'; % regular expression.
% Read old file and replace data:
old = fileread('bp.txt');
new = regexprep(old,rgx,rpl);
% Save the new file:
fid = fopen('bp_new.txt','wb');
fprintf(fid,'%s',new);
fclose(fid)
The input and output files are attached.
  23 Comments
Idin Pushkin
Idin Pushkin on 9 May 2019
Edited: Idin Pushkin on 9 May 2019
str = fileread('bp.txt');
% ^^^^ What is this supposed to do?
it was spelling mistake about the above code. about the loop u said i use this code and doesnt work again
for i=1:length(vec)
str(idx) = regexprep(str(idx),'^[^*]+',num2str(vec(i)));
fid = fopen(newStr1,'wb');
fprintf(fid,'%s\n',str{:});
fclose(fid);
end
Stephen23
Stephen23 on 10 May 2019
I wrote "with indexing into the vectors idx and vec..."
You are using i with vec (which is good) and ignored idx (which is not good).
You can see that the elements of idx correspond to the elements of vec... therefore if you use indexing into vec then you will also need exactly the same indexing into idx (just as I wrote in my comment).
Note the putting the file writing code inside that loop just overwrites the file contents on each iteration. In the end, only the last iteration will remain, so there is no point in this being isnide the loop (apart from slowing down your code and heating up your room).

Sign in to comment.

More Answers (1)

KSSV
KSSV on 3 May 2019
Edited: KSSV on 3 May 2019
fid = fopen('data.txt','r') ;
S = textscan(fid,'%s','delimiter','\n') ;
fclose(fid) ;
S = S{1} ;
% Get indices Tsteps
idx = find(contains(S,'TSTEP'))+1 ;
% Replace the number
S1 = S ;
S1(idx) = {'2.5*100'} ;
% Write to file
fid = fopen('test.txt','w') ;
fprintf(fid,'%s\n',S1{:});
fclose(fid);
NOTE: If contains is not available, you can use strcmp, ismember.
  8 Comments
Idin Pushkin
Idin Pushkin on 3 May 2019
it doesnt make a difference. makes 1*2 cell arrays.
Walter Roberson
Walter Roberson on 3 May 2019
Your idx is non-scalar because you have multiple matches in the file. extractAfter needs to return multiple values.

Sign in to comment.

Tags

No tags entered yet.

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!