MATLAB Answers

0

FileCopy does't work

Asked by sriram shastry on 7 Sep 2019
Latest activity Commented on by sriram shastry on 18 Sep 2019
Copying files from source directory to destination directory is NOT working.
Below is my source code. Please help me
WorkingDir = 'C:\Users\shastry\MathWorks\test_that_results_hatch_B1CYKd';
OutputFolder = fullfile(WorkingDir, 'Tmp');
if ~exist(OutputFolder, 'dir')
mkdir(OutputFolder);
end
Param.Source = WorkingDir; %'C:\Users...';
Param.Target = OutputFolder; %'C:\Users...';
Files=dir(fullfile(Param.Source,'**\*.*'));
Files = Files(~[Files.isdir]); % Remove folders from list;
for k = 1:length(Files)
if contains(Files(k).folder,'debug')
if contains(Files(k).name,'test_that')
CurrentFile = Files(k).name;
exist(CurrentFile,'file') % 1=exist 0=doesn't exist
RenameFile= regexprep(CurrentFile,{'\.'},{''}); % Replace dot from Files.name
exist(RenameFile,'file') % 1=exist 0=doesn't exist
copyfile(fullfile(Param.Source, CurrentFile), fullfile(Param.Target, RenameFile));% copy sourcefolder file to destnationfolder file
end
end
end

  5 Comments

I have rewritten the code as below , it copies the ranamed file to OutputFolder directory
WorkingDir = 'C:\Users\shastry\MathWorks\test_that_results_hatch_B1CYKd';
OutputFolder = fullfile(WorkingDir, 'Tmp');
if ~exist(OutputFolder, 'dir')
mkdir(OutputFolder);
end
Param.Source = WorkingDir; %'C:\Users...';
Param.Target = OutputFolder; %'C:\Users...';
Files=dir(fullfile(Param.Source,'**\*.*'));
Files = Files(~[Files.isdir]); % Remove folders from list;
for k = 1:length(Files)
%debug subfolder
if contains(Files(k).folder,'debug') % look for folder with debug name
if contains(Files(k).name,'test_that') % look for file with test_that name
RenameFile = regexprep(Files(k).name,{'\.'},{''}); % Replace dot Files.name
[SUCCESS,MESSAGE,MESSAGEID] = copyfile(fullfile(Files(k).folder ,Files(k).name), fullfile(Param.Target, RenameFile));% copy sourcefolder file to destnationfolder file
end
end
% result- subfolder
if contains(Files(k).folder,'results-') % look for folder with results-
if contains(Files(k).name,'autoserv') % look for file with autoserv
RenameFile = regexprep(Files(k).name,{'\.'},{''}); % Replace dot Files.name
[SUCCESS,MESSAGE,MESSAGEID] = copyfile(fullfile(Files(k).folder ,Files(k).name), fullfile(Param.Target, RenameFile));% copy sourcefolder file to destnationfolder file
end
end
%firmware_ subfolder
if contains(Files(k).folder,'firmware_') % look for folder with firmware_
if contains(Files(k).name,'firmware_') % look for file with test_that name
RenameFile = regexprep(Files(k).name,{'\.'},{''}); % Replace dot Files.name
[SUCCESS,MESSAGE,MESSAGEID] = copyfile(fullfile(Files(k).folder ,Files(k).name), fullfile(Param.Target, RenameFile));% copy sourcefolder file to destnationfolder file
end
end
end
Guillaume
on 8 Sep 2019
That looks much better, you're now using the actual folder where the file is found.
I assume your problem is solved?
I don't understand your comment about the . in the file name. Matlab IO functions don't care one bit about the format of the filename, you can have as many or as few . in the filename, it won't change anything.
Note that it would be clearer if you passed char arrays to to regexprep instead of scalar cell arrays:
RenameFile = regexprep(Files(k).name, '\.', '');
%or
RenameFile = strrep(Files(k).name, '.', '');
and the whole lot, if it's needed would be better written only once before the ifs.
Also the double ifs could be written as just one:
if contains(Files(k).folder,'debug') && contains(Files(k).name,'test_that')
Thanks a lot for your help . I incorparated your feedback to my code.
WorkingDir = 'C:\Users\shastry\MathWorks\test_that_results_hatch_B1CYKd';
OutputFolder = fullfile(WorkingDir, 'Temp');
if ~exist(OutputFolder, 'dir')
mkdir(OutputFolder);
end
Param.Source = WorkingDir; %'C:\Users...';
Param.Target = OutputFolder; %'C:\Users...';
Files=dir(fullfile(Param.Source,'**\*.*'));
Files = Files(~[Files.isdir]); % Remove folders from list;
debug = 0;
autoserv = 0;
firmware = 0;
for k = 1:length(Files)
%debug subfolder
if contains(Files(k).folder,'debug') && contains(Files(k).name,'test_that') % look for folder & file
RenameFile = regexprep(Files(k).name,'\.',''); % Replace dot Files.name
[SUCCESS,MESSAGE,MESSAGEID] = copyfile(fullfile(Files(k).folder ,Files(k).name), fullfile(Param.Target, RenameFile));% copy sourcefolder file to destnationfolder file
if SUCCESS ==1
debug = debug+1;
Content.test_that{k,debug} = get_debug(Param.Target, RenameFile,debug);
end
end
% result- subfolder
if contains(Files(k).folder,'results-') && contains(Files(k).name,'autoserv') % look for folder & file
RenameFile = regexprep(Files(k).name,'\.',''); % Replace dot Files.name
[SUCCESS,MESSAGE,MESSAGEID] = copyfile(fullfile(Files(k).folder ,Files(k).name), fullfile(Param.Target, RenameFile));% copy sourcefolder file to destnationfolder file
if SUCCESS ==1
autoserv = autoserv+1;
Content.autoserv{k,autoserv} = get_debug(Param.Target, RenameFile,autoserv);
end
end
%firmware_ subfolder
if contains(Files(k).folder,'firmware_') && contains(Files(k).name,'firmware_') % look for folder & file
RenameFile = regexprep(Files(k).name,'\.',''); % Replace dot Files.name
[SUCCESS,MESSAGE,MESSAGEID] = copyfile(fullfile(Files(k).folder ,Files(k).name), fullfile(Param.Target, RenameFile));% copy sourcefolder file to destnationfolder file
if SUCCESS ==1
firmware = firmware+1;
Content.firmwarefirmware{k,firmware} = get_debug(Param.Target, RenameFile,firmware);
end
end
end
get_debug function has
function [Content] = get_debug(path,filename,idx)
filename = dir(fullfile(path,filename));
VariableNames = {'Date', 'log', 'Sublog', 'Message', 'Dummy1', 'Dummy2'};
VariableWidths = [19, 6, 25, 5000, 1, 1];%[19, 98, 1, 1, 1, 1];
VariableTypes = {'datetime', 'char', 'char', 'char', 'char', 'char'};
opts = fixedWidthImportOptions('VariableNames', VariableNames, 'VariableWidths', VariableWidths, 'VariableTypes', VariableTypes, 'SelectedVariableNames', [1, 2, 3, 4]);
opts = setvaropts(opts, 'Date', 'InputFormat', 'MM/yy HH:mm:ss.SSS');
dataFile = fullfile(filename.folder,filename.name);
Content{idx} = readtable(dataFile, opts);
But now the real problem comes from the code you suggested sometime ago.
[contentfields] = fieldnames(Content);
for fieldidx = 1:numel(contentfields) %iterate over each field of Content
structtable = struct2cell(Content.(contentfields{fieldidx})); %extract the structure within the field by converting it to cell array (avoids having to work out what its name is)
% structtable = Content.(contentfields{fieldidx}); %extract the structure within the field by converting it to cell array (avoids having to work out what its name is)
structtable = structtable{1}; %get the table out of the cell
structtable.Date = duration(structtable.Date.Hour, structtable.Date.Minute, structtable.Date.Second); %extract h/m/s and make that a duration.
structtable.Date = structtable.Date - structtable.Date(1); %elapsed time since start of log.
structtable.Properties.VariableNames{1} = 'WeirdDuration'; %rename the time column {system time logs are wired}
structtimetable = table2timetable(structtable(:, {'WeirdDuration','Message'})); %convert to timetable, only keeping Date and Message
structtimetable.Properties.VariableNames{1} = sprintf('Message_%s', contentfields{fieldidx}); %rename Message variable so we know where it came from
structtimetable = rmmissing(structtimetable); %remove invalid rows to avoid problems with synchronize
structtimetable.Properties.RowTimes.Format = 'hh:mm:ss.SSS'; %duration format to support millisecond
if fieldidx == 1
joinedtimetable = structtimetable; %1st time, create output
else
fieldidx
joinedtimetable = synchronize(joinedtimetable, structtimetable, 'union'); %subsequent times, synchronize. Choose whichever method is prefered
end
end
I am getting below error
Matlab console error
Undefined function 'struct2cell' for input arguments of type 'cell'.
struct2cell doesn't work for me. and I am finding it difficult resolve . For reference I have added the *.mat file for content data. Can you please help me . Thanks
Content =
struct with fields:
test_that: {26×2 cell}
autoserv: {30×4 cell}
firmwarefirmware: {34×4 cell}
for,
filecopy_new.mat
Content =
struct with fields:
test_that: {12×2 cell}
autoserv: {16×4 cell}
firmwarefirmware: {20×4 cell}

Sign in to comment.

2 Answers

Guillaume
Answer by Guillaume
on 9 Sep 2019
 Accepted Answer

I don't remember the details of your previous question, but clearly the code I gave you is meant to work with data imported a particular way. If you change the way you import the data, it's not going to work. Reading the code above Content must be a scalar structure where each field is itself a scalar structure with just one field which is a table.
In your mat file, Content is a cell array, not a structure as expected. So yes, you'll get an error but not the one you mention (it's fieldnames that would complain first). The cell array can trivially be converted into a structure but the substructures contain more than one table. As it is, the code would only use the first table. The code would have to be modified to cope with more than one table per structure, but it's unclear what you want to do.
Furthermore, the Content description you pasted above doesn't match your attached mat file. Above, Content is indeed a structure as expected, but the fields contain cell arrays, not structures. So, yes you'll get a struct2cell error from that.
I think I told you before, if the format of your input keep on changing don't expect the solutions you're given to work anymore. It's important to be consistant.

  19 Comments

OK, Then how to proceed? Please help me. Thanks!
Guillaume
on 17 Sep 2019
I don't know yet. It may not be simple.
In any case, it's a completely different question from what you originally asked, so you should start a new one.The two timetable examples I gave above would probably be a good start for that new question.
Thanks a ton for all learnings i received from you!

Sign in to comment.


Answer by sriram shastry on 17 Sep 2019
Edited by sriram shastry on 17 Sep 2019

I used below code.
contentfields = fieldnames(Content);
for fieldidx = 1:numel(contentfields) %iterate over each field of Content
substruct = Content.(contentfields{fieldidx}); %which are structure arrays containing tables
subfields = fieldnames(substruct);
for subelem = 1:numel(substruct) %iterate over each element of the array
for subfieldidx = 1:numel(subfields) %iterate over the subfields
structtable = substruct(subelem).(subfields{subfieldidx}); %and get the table out of it
structtable.Date = duration(structtable.Date.Hour, structtable.Date.Minute, structtable.Date.Second); %extract h/m/s and make that a duration.
structtable.Date = structtable.Date - structtable.Date(1); %elapsed time since start of log.
structtable.Properties.VariableNames{1} = 'WeirdDuration'; %rename the time column
structtable.Properties.VariableNames(2:end) = strcat(structtable.Properties.VariableNames(2:end), sprintf('_%s%d_%s', contentfields{fieldidx}, subelem, subfields{subfieldidx})); %append content field name and subfield name to remaining table variables
structtimetable = table2timetable(structtable); %convert to timetable
structtimetable = rmmissing(structtimetable); %remove invalid rows to avoid problems with synchronize
structtimetable.Properties.RowTimes.Format = 'hh:mm:ss.SSS'; %duration format to support millisecond
if fieldidx == 1 && subelem == 1 && subfieldidx == 1
joinedtimetable = structtimetable; %1st time, create output
else
joinedtimetable = synchronize(joinedtimetable, structtimetable, 'union'); %subsequent times, synchronize. Choose whichever method is prefered
end
end
end
end
I captured the output . I listed out finding and problems in the below table
Please see below table for output difference's
+------------------------------------------+-----------------------------------------+
| Bad-case ( info is unavailable) | Good-case (full info available) | |
+------------------------------------------+-----------------------------------------+
|joinedtimetable.Message_faft_client1_faft |structtimetable.Message_faft_client1_faft|
|joinedtimetable.Message_cr50_uart1_cr50 |joinedtimetable.Message_autoserv1_debug |
|joinedtimetable.Message_ec_uart1_ec |joinedtimetable.Message_autoserv2_debug |
| |joinedtimetable.Message_autoserv3_debug |
| |joinedtimetable.Message_autoserv4_debug |
| |joinedtimetable.Message_firmware1_debug |
| |joinedtimetable.Message_firmware2_debug |
| |joinedtimetable.Message_firmware3_debug |
| |joinedtimetable.Message_firmware4_debug |
| |joinedtimetable.Message_test_that1_debug |
| |joinedtimetable.Message_test_that2_debug |
| |joinedtimetable.Message_test_that3_debug |
| |joinedtimetable.Message_test_that4_debug |
+------------------------------------------+-----------------------------------------+
I don't see Message Content . I want your help in resolving this issue
"joinedtimetable_output.txt". full output of joinedtimetable is available.
In this file I am referring the content of
Message_cr50_uart1_cr50,
Message_faft_client1_faft,
Message_ec_uart1_ec is missing .
I can see Message Content for below data
Message_test_that1_debug ,
joinedtimetable.Message_autoserv1_debug ,
joinedtimetable.Message_firmware1_debug
[ 1 to 4 represent file number]
This section is perfect. Timeseries is aligned with message content
I think the issue with structure & it seems they are overwritten
joinedtimetable.Message_faft_client1_faft
joinedtimetable.Message_ec_uart1_ec
joinedtimetable.Message_cr50_uart1_cr50

  0 Comments

Sign in to comment.