matlab iterative filenames for saving - string

this question about matlab:
i'm running a loop and each iteration a new set of data is produced, and I want it to be saved in a new file each time. I also overwrite old files by changing the name. Looks like this:
name_each_iter = strrep(some_source,'.string.mat','string_new.(j).mat')
and what I#m struggling here is the iteration so that I obtain files:
...string_new.1.mat
...string_new.2.mat
etc.
I was trying with various combination of () [] {} as well as 'string_new.'j'.mat' (which gave syntax error)
How can it be done?

Strings are just vectors of characters. So if you want to iteratively create filenames here's an example of how you would do it:
for j = 1:10,
filename = ['string_new.' num2str(j) '.mat'];
disp(filename)
end
The above code will create the following output:
string_new.1.mat
string_new.2.mat
string_new.3.mat
string_new.4.mat
string_new.5.mat
string_new.6.mat
string_new.7.mat
string_new.8.mat
string_new.9.mat
string_new.10.mat

You could also generate all file names in advance using NUM2STR:
>> filenames = cellstr(num2str((1:10)','string_new.%02d.mat'))
filenames =
'string_new.01.mat'
'string_new.02.mat'
'string_new.03.mat'
'string_new.04.mat'
'string_new.05.mat'
'string_new.06.mat'
'string_new.07.mat'
'string_new.08.mat'
'string_new.09.mat'
'string_new.10.mat'
Now access the cell array contents as filenames{i} in each iteration

sprintf is very useful for this:
for ii=5:12
filename = sprintf('data_%02d.mat',ii)
end
this assigns the following strings to filename:
data_05.mat
data_06.mat
data_07.mat
data_08.mat
data_09.mat
data_10.mat
data_11.mat
data_12.mat
notice the zero padding. sprintf in general is useful if you want parameterized formatted strings.

For creating a name based of an already existing file, you can use regexp to detect the '_new.(number).mat' and change the string depending on what regexp finds:
original_filename = 'data.string.mat';
im = regexp(original_filename,'_new.\d+.mat')
if isempty(im) % original file, no _new.(j) detected
newname = [original_filename(1:end-4) '_new.1.mat'];
else
num = str2double(original_filename(im(end)+5:end-4));
newname = sprintf('%s_new.%d.mat',original_filename(1:im(end)-1),num+1);
end
This does exactly that, and produces:
data.string_new.1.mat
data.string_new.2.mat
data.string_new.3.mat
...
data.string_new.9.mat
data.string_new.10.mat
data.string_new.11.mat
when iterating the above function, starting with 'data.string.mat'

Related

Removing \n from a list

so i'm currently learning about mail merging and was issued a challenge on it. The idea is to open a names file, read the name on the current line and then replace it in the letter and save that letter as a new item.
I figured a good idea to do this would be a for loop.
Open file > for loop > append names to list > loop the list and replace ect.
Except when I try to actually append the names to the list, i get this:
['Aang\nZuko\nAppa\nKatara\nSokka\nMomo\nUncle Iroh\nToph']
The code I am using is:
invited_names = []
with open ("./Input/Names/invited_names.txt") as names:
invited_names.append(names.read())
for item in invited_names:
new_names = [str.strip("\n") for str in invited_names]
print(new_names)
Have tried to replace the \n and now .strip but I have not been able to remove the \n. Any ideas?
EDIT: not sure if it helps but the .txt file for the names looks like this:
Aang
Zuko
Appa
Katara
Sokka
Momo
Uncle Iroh
Toph
As you can see, read() only returns a giant string of what you have in your invited_names.txt file. But instead, you can use readlines() which returns a list which contains strings of every line (Thanks to codeflush.dev for the comment). Then use extend() method to add this list to another list invited_names.
Again, you are using for loop and list comprehension at the same time. As a result, you are running the same list comprehension code for many times. So, you can cut off any of them. But I prefer you should keep the list comprehension because it is efficient.
Try this code:
invited_names = []
with open ("./Input/Names/invited_names.txt") as names:
invited_names.extend(names.readlines()) # <--
new_names = [str.strip("\n") for str in invited_names]
print(new_names)

Matlab sprintf incorrect result using random strings from list

I want create a string variable using ´sprintf´ and a random name from a list (in order to save an image with such a name). A draft of the code is the following:
Names = [{'C'} {'CL'} {'SCL'} {'A'}];
nameroulette = ceil(rand(1)*4)
filename = sprintf('DG_%d.png', Names{1,nameroulette});
But when I check filename, what I get is the text I typed followed not by one of the strings, but by a number that I have no idea where it comes from. For example, if my nameroulette = 1 then filename is DG_67.png, and if nameroulette = 4, filename = 'DG_65.png' . Where does this number come from and how can I fix this problem?
You just need to change
filename = sprintf('DG_%d.png', Names{1,nameroulette});
to
filename = sprintf('DG_%s.png', Names{1,nameroulette});
By the way you may want to have a look at randi command for drawing random integers.

(matlab) unique variable name from string

I have a simple script to import some spectroscopy data from files with some base filename (YYYYMMDD) and a header. My current method pushes the actual spectral intensities to some vector 'rawspectra' and I can call the data by `rawspectra{m,n}.data(q,r)
In the script, I specify by hand the base filename and save it as a string 'filebase'.
I would like to append the name of the rawspectra vector with the filebase so I might be able to use the script to import files acquired on different dates into the same workspace without overwriting the rawspectra vector (and also allowing for easy understanding of which vectors are attached to which experimental conditions. I can easily do this by manually renaming a vector, but I'd rather make this automatic.
My importation script follows:
%for the importation of multiple sequential files, starting at startfile
%and ending at numfiles. All raw scans are subsequently plotted.
numfiles = input('How many spectra?');
startfile = input('What is the starting file number?');
numberspectra = numfiles - (startfile - 1);
filebase = strcat(num2str(input('what is the base file number?')),'_');
rawspectra = cell(startfile, numberspectra);
for k= startfile:numberspectra
filename = strcat(filebase,sprintf('%.3d.txt', k));
%eval(strcat(filebase,'rawspectra')){k} = importdata(filename); - This does not work.
rawspectra{k} = importdata(filename);
figure;
plot(rawspectra{1,k}.data(:,1),rawspectra{1,k}.data(:,2))
end
If any of you can help me out with what should be a seemingly simple task, I would be very appreciative. Basically, I want 'filebase' to go in front of 'rawspectra' and then increment that by k++ within the loop.
Thanks!
Why not just
rawspectra(k) = importdata(filename);
rawspectra(k).filebase = filebase;

How can i list all the files in a folder with a specific name in matlab?

I have been making a loop that assign Mx names for 121 different files in a folder.
allFiles = dir( '*.xls''String' );
allNames = { allFiles.name };
for ii = 1:length(allNames) M(ii) = xlsread(allFiles(1i));
end
Trouble is that there is no errormessage, but it isn't assigning any names for the values/files i want it to.
listing = dir('*.xls');
disp(listing);
When i make a simple dir() it tells me
121x1 struct array with fields:
name
date
bytes
isdir
datenum
But i have to make it a String in order for xlsread() to work.
What i want it to is to make a name for each file so i can handle them in matlab, (ie. addtion of two matrices).
What can be wrong?
This question is basically just typos and confusion of variables:
allFiles = dir('*.xls'); % correct file extension
for ii = 1:size(allFiles, 1) % allFiles has one row per file, so loop over those
M{ii} = xlsread(allFiles(ii).name); % store matrix in cell array
end
Note that M is now a cell array, because you can't store multiple matrices in a matrix or vector.

I want to export the name of multiple matlab files into a .csv

I want to use a for loop to export the names of a folder of .mat files into one .csv file by row.
I am trying to use xlswrite, but don't understand how to access the filename of the .mat files.
I am working with to write them to the csv.
xlswrite(fullfile(dest_dir,'result.csv'), FILENAME HERE, ['A' num2str(i)]);
xlswrite creates a excel workbook
With dir command you can get a structure whose one of field is name of file.
Using simple file IO function your requirement can be met.
I think either of this will do what you need:
fid=fopen('result.csv','wt');
files=dir('*.mat');
x={files(:).name};
csvFun = #(str)sprintf('%s,',str);
xchar = cellfun(csvFun, x,'UniformOutput', false);
xchar = strcat(xchar{:});
xchar = strcat(xchar(1:end-1),'\n');
fprintf(fid,xchar);
fclose(fid);
Or
If you just need .mat names in a column form:
fid=fopen('result.csv','wt');
files=dir('*.mat');
x={files(:).name};
[rows,cols]=size(x);
for i=1:rows
fprintf(fid,'%s,',x{i,1:end-1});
fprintf(fid,'%s\n',x{i,end});
end
fclose(fid);
To get your filename, load the files using dir command, read them individually in your for loop, and then write them to file. (I think I already posted something like this?) Here is the prototype:
files = dir('*.mat'); % obtain all files with .mat extenstion
fid = fopen('result.csv','a');
for k = 1:length(data)
filename = files(k).name; % get the filename
fprintf(fid, '%s,\n', filename);
end
fid = fclose(fid);
Unfortunately, you cannot just save the file names as strings in a cell and write it as you might a matrix using say csvwrite, so you can just do this.

Resources