Write vectors of different size in text file

8 views (last 30 days)
Hello everybody,
I would like to write some data to a text-file. Unfortunately the dimensions of the data are not the same, so I get the error:
Error using horzcat
Dimensions of matrices being concatenated are not consistent.
Filename_txt = 'Dummy.txt'
data = [Angle Velocity Distance Acceleration]';
fidwrite = fopen(Filename_txt, 'wb');
fprintf(fidwrite, '%s\t %s\t %s\t %s\n', 'Angle[deg]','Velocity[mm/s]','Distance [mm]', 'Acceleration [mm/s^2]');
status = fprintf(fidwrite, '%4.5f\t %4.5f\t %4f.5\t %4.5f\n', data);
fclose(fidwrite);
disp (['txt-File ' Filename_txt ' created']);
Is it possible to write the data into one text-file even though they differ in their dimensions?
Thank you
Christian
  4 Comments
Adam
Adam on 1 Feb 2017
But where do the extra 6 values come from? Are they just on their own at the end? Do the previous 274 match up to the 274 of the Distance vector or are there just 6 values missing from the Distance vector at arbitrary locations?
You can probably just pad your shorter vectors with NaNs if the extra numbers are all at the end. Then they will all be the same size.
Christian
Christian on 1 Feb 2017

Distance, Acceleration etc. are just dummy names. To make my point clear, you can also use the population of cities as an example:

data = [Cities_in_Europe Population_of_cities_in_Europe Cities_in_the_US Population_of_cities_in_the_US]';

Result:

Cities_Europe  Pop_cities_Europe  Cities_USA  Pop_cities_USA
Paris             3.000.000         New York    5.000.000
Berlin            2.500.000        Los Angeles  4.000.000
London            6.000.000

Cities_Europe and Cities_USA are two independent vectors with a different size (3x1 vs 2x1). But I want them to be in the same text file for further handling in different software.

I hope that makes my point clear?

Sign in to comment.

Accepted Answer

dpb
dpb on 1 Feb 2017
Edited: dpb on 2 Feb 2017
data = [Angle Velocity Distance Acceleration]';
...
where not all vectors are of same length.
Doesn't seem to make much sense if the missing values of the shorter observations are scattered, so simply augment the shorter with NaN or some other indicator value based on length of longest before the concatenation operation.
Or, of course, while a little more work, you could loop through for 1:max(lengths) and write row by row testing for whether there is value for each variable and using a count-specific fprintf argument list and a fill string for the missing column(s). Obviously, the first solution is simpler.
Of course, whether the result makes any sense or not is another issue... :)
ADDENDUM
OK, the example given would have to be a cell array to be concatenated and fprintf isn't able to handle cell arrays as arrays any way. You will have to make sizes commensurate with missing value indicators if you insist on the concatenation route.
If all were numeric as would be presumed from original variables names, then you could have two operations; concatenate the subsections of same size and fprintf them, then fprintf the subsection of longer elements as a second array.
But, for the mixed data you'll have to loop irregardless unless you were to import to a table (again will need missing value indicators, though). Then writetable might be able to deal with it for you although you'd have to convert the numerics to string inside the table methinks to be able to get the blank rows; missing values as NaN for numbers would still show up.
If were all numeric then something like
nR=[size(Angle,1) size(Velocity,1) size(Distance,1) size(Acceleration,1)];
dR=max(nR)-nR;
data=[Angle;nan(dR(1),1) Velocity;nan(dR(1),1) Distance;nan(dR(1),1) Acceleration;nan(dR(1),1)];
would fill the shorter columns with NaN to be able to concatenate. Of course, then the output would contain NaN which is probably not what want.
For the second example, it takes some more effort. If the four variables are cellstrings for the cities and numeric for the populations, then the following script is crude outline--
N=2; % repetition count for the formatting substring
fmt=[repmat('% 12s % 8d ',1,N) '\n']; % build the appropriate format string
N1=min(length(Cities_Eur),length(Cities_US)); % shorter loop upper limit
for i=1:N1
fprintf(fmt,char(Cities_Eur(i)),Pop_Eur(i),char(Cities_US(i)),Pop_USA(i))
end
N=1; fmt=[repmat('% 12s % 8d ',1,N) '\n']; % update format string
for i=N1+1:length(Cities_Eur) % complete the output over longer arrays
fprintf(fmt,char(Cities_Eur(i)),Pop_Eur(i))
end
This yields
Paris 3000000 New York 5000000
Berlin 2500000 Los Angeles 4000000
London 6000000
Adding the header is another line first, of course.
Specialized output requires specialized coding for it, unfortunately...
  3 Comments
Christian
Christian on 2 Feb 2017
dpb, I appreciate your answer! But since I'm rather new to matlab I have honestly no idea what you are talking about. Maybe you can make your point clear with a few lines of code?
Christian
Christian on 2 Feb 2017
Thank you! I tried to modify your code for my needs and it seems very promising! If I will face any further problems, I will let you know.
But thank you for now!

Sign in to comment.

More Answers (0)

Community Treasure Hunt

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

Start Hunting!