File Exchange

image thumbnail

struct2xml

version 1.7 (3 KB) by

Convert a MATLAB structure into a XML file.

47 Downloads

Updated

View License

This function converts a MATLAB structure into a XML file.

Comments and Ratings (30)

it must bu a cell of structures:

m code :
<elem name="name" desc="description">
    <subelem name="name3" desc="description3" number="3"/>
    <subelem name="name5" desc="description5" number="5"/>
</elem>

xml :
elem.Attributes.name = 'name';
elem.Attributes.desc = 'description';
elem.subelem{1}.Attributes.name = 'name3';
elem.subelem{1}.Attributes.desc = 'description3';
elem.subelem{1}.Attributes.number = '3';
elem.subelem{2}.Attributes.name = 'name5';
elem.subelem{2}.Attributes.desc = 'description5';
elem.subelem{2}.Attributes.number = '3';

What format does the struct have to be? Seems that it breaks if there are nested structures.

Herve Demezil

To fix the bug with matlab r2016a replace line 166 in function "val2str()":
str = [];
by
str = '';

I've tried and it seems to fix it

Herve Demezil

Did you fix the bug?

Override

xmlwrite.m crashes at Line 82 in R2016a

The reason could be the "new" Java version in combination with JAXP (which is used by MATLAB):
http://stackoverflow.com/questions/21393323/jaxb-marshaller-throwing-nullpointerexception-when-upgrading-from-java-6-to-java

Amos

Amos (view profile)

struct2xml bombs with a Java exception in R2016a, if the structure has empty entries. The problem did not occur in earlier MATLAB versions.

Can someone please fix that?

superaga

Ilya Belevich

Raúl

Raúl (view profile)

Great script. I don't know why my struct 'S' is not written in a xml file. I'm using the following statement

file = struct2xml(S);

Where 'file' is the xml file where I want to save the struct and S my struct. However, non xml file is created. Can you help me? What am I missing?
Thanks

Really nice

Fredrik

Rody Oldenhuis

Rody Oldenhuis (view profile)

Graham

Graham (view profile)

Thanks! To get it to support logical fields, I broadened the condition of line 172 (val2str):

elseif (isnumeric(val) || islogical(val))
    val = num2str(val);

Timo Dörsam

Many thanks. It does work fine for me.

Hugo

Hugo (view profile)

I have one .mat file and I need to convert it to a .xml file. Can anyone help me how to use the function. I always got an error about the input parameters.

Wouter Falkena

Wouter Falkena (view profile)

Hi Harald,

The reason why the function requires a single field in the main structure is that a properly formatted XML document has a single root element (http://www.w3schools.com/xml/xml_dtd.asp). The only exception to that rule is a more elaborate XML preamble, which is currently not supported by the function.

For the second point, XML files usually have multiple elements with the same name. In order to convert this into a MATLAB structure, an array may be used. This means that isstruct(s.(curfield)) indeed may not work, but in that case
if iscell(s.(curfield))
  min(cellfun(@(a) isstruct(a),s.curfield))
end
will tell you if all cells in the array are structures.

I hope this clarifies how to use the function a bit. If you have any more questions feel free to contact me.

Regards,
Wouter

I had high hopes after reading the reviews, but... "There should be a single field in the main structure" - why? But worse: for an array of struct the call "isstruct(s.(curfield)" crashes because the return value ia an array!

Wouter Falkena

Wouter Falkena (view profile)

Hi Emil,

The function indeed replaces the characters -:. with _ (also see the function help). It should be possible to rewrite the function to replace : with something unique like _colon_ and let struct2xml replace this with :. Let me know if you still need this functionality. The structure names do get longer in that way...

Regards,
Wouter

Emil

Emil (view profile)

Great Script... Just one question. I noticed when I loaded an XML with XML2struct it

<?xml version="1.0" encoding="utf-8"?>
<ADE:Recipe xmlns:ADEL

Then export with Struct2XML I get

<?xml version="1.0" encoding="utf-8"?>
<ADE_Recipe xmlns_ADE
 
The : were replaced with _
It seems to pop up because the Root and Attributes are structs while in MatLab and Matlab won't allow : character for struct.

I'm ok If this doesn't effect the validity of the file. If it does, I'm gong to have to make some modifications :(

Wouter Falkena

Wouter Falkena (view profile)

Thank you Herbert for finding and successfully eradicating this bug. I have uploaded the fixed file to the MATLAB Central.

Great tool. Helped a lot. But I found a little bug. Trying to convert something like:
a.b.Text = '';
b = struct2xml(a) throws an exception because of a bug in val2str(...).

The simple solution is to replace

...
if (isempty(val))
%do nothing
...

by

if (isempty(val))
return;

in function val2str(...)

Wouter Falkena

Wouter Falkena (view profile)

You are correct. However, isspace does not operate on cells. In the latest update I removed the for-loop all together and use isspace on the multi-line string. This is the fastest approach yet. Again, thank you for your support.

T Lohuis

Thank you Wouter for keeping the function updated!

Correct me if i'm wrong, but in my test the whitespace approach with isspace is about 40 times faster than regexprep. (i use an very long array, [148701x1 double], values )

Replaced:
str_cell = regexprep(tmp_cell,'[ ]*', ' ');

With:
whitespace=isspace(tmp_cell(:));
nonspace=(whitespace+ [0 whitespace(1:end-1)])~=2;
str_cell = tmp_cell(nonspace);

Wouter Falkena

Wouter Falkena (view profile)

Thank you thijs for bringing this to my attention. The problem lies not in the regexprep, but in the for loop, however. I have changed the for loop to build a cell array of the multiline sting and execute the regexprep only once. From the MATLAB profiler I obtained that your method is already 38% faster. The regexprep using the cell should be 160% faster than before. I will upload the new function today and hopefully it will be available from Mathworks tomorrow. Thanks again for the suggestion!

T Lohuis

T Lohuis

For longer arrays of values it takes very long processing!, Use this
--
whitespace=isspace(tmp(i,:));
nonspace=(whitespace+ [0 whitespace(1:end-1)])~=2; % Only double whitespaces are removed)
str = [str tmp(i,nonspace) sprintf('\n')]
--

instead off:
--
str = [str regexprep(tmp(i,:),'[ ]*', ' ') sprintf('\n')];
--

Mais

Mais (view profile)

very easy to use. thank you very much

Philipp Orth

Fast and works like expected for everything I tried up to now (which is not the case for the other Struct<->XML conversions I found at Matlab Central in the last years). Thanks a lot.

Updates

1.7

The function now replaces element and attribute names containing _dash_ by -, _dot_ by . and _colon_ by :

1.6

Bugfix in val2str subfunction

1.5

Removed the for-loop in the val2str subfunction, thereby increasing the speed drastically.

1.4

Increased the speed of the str2val subfunction by removing the for-loop and making use of the suggestion of T. Lohuis.

1.3

Improved processing speed for multiline strings (or arrays) by 160%.

1.2

Added the on-screen output functionality suggested by Philipp Orth

1.1

Added a warning for ill-formatted Attributes

MATLAB Release
MATLAB 7.7 (R2008b)

Download apps, toolboxes, and other File Exchange content using Add-On Explorer in MATLAB.

» Watch video