# HG changeset patch # User Jordi GutiƩrrez Hermoso # Date 1353446221 18000 # Node ID 808e4f13e220cc7fd69f249bcb78eeed0e9736ce # Parent f2b8f90052fd85699fb59a08e40b0b0f8ddf36ee doc: Update struct documentation to match new indexing rules * container.txi: Mention that fields can now be arbitrary strings and issues that this may cause with Matlab. * setfield.m: Completely rewrite docstring. More examples. * getfield.m: Remove most of the docstring and refer to setfield's docstring instead. diff -r f2b8f90052fd -r 808e4f13e220 doc/interpreter/container.txi --- a/doc/interpreter/container.txi Tue Nov 20 13:24:51 2012 -0500 +++ b/doc/interpreter/container.txi Tue Nov 20 16:17:01 2012 -0500 @@ -38,9 +38,9 @@ @cindex structures @cindex data structures -Octave includes support for organizing data in structures. The current +Octave includes support for organizing data in structures. The current implementation uses an associative array with indices limited to -strings, but the syntax is more like C-style structures. +strings, but the syntax is more like C-style structures. @menu * Basic Usage and Examples:: @@ -390,6 +390,28 @@ @end group @end example +@noindent +Dynamic indexing also allows you to use arbitrary strings, not merely +valid Octave identifiers (note that this does not work on @sc{Matlab}): + +@example +@group +a = "long field with spaces (and funny char$)"; +x.a = 1; +x.(a) = 2; +x + @result{} x = + @{ + a = 1 + long field with spaces (and funny char$) = 2 + @} +@end group +@end example + +@noindent +The warning id @code{Octave:matlab-incompatible} can be enabled to warn +about this usage. @xref{doc-warning_ids}. + More realistically, all of the functions that operate on strings can be used to build the correct field name before it is entered into the data structure. @@ -471,7 +493,7 @@ field2 = 2 @} @end group - @end example +@end example @DOCSTRING(struct) @@ -491,9 +513,9 @@ @DOCSTRING(isfield) -@DOCSTRING(getfield) +@DOCSTRING(setfield) -@DOCSTRING(setfield) +@DOCSTRING(getfield) @DOCSTRING(rmfield) diff -r f2b8f90052fd -r 808e4f13e220 scripts/miscellaneous/getfield.m --- a/scripts/miscellaneous/getfield.m Tue Nov 20 13:24:51 2012 -0500 +++ b/scripts/miscellaneous/getfield.m Tue Nov 20 16:17:01 2012 -0500 @@ -18,28 +18,12 @@ ## . ## -*- texinfo -*- -## @deftypefn {Function File} {[@var{v1}, @dots{}] =} getfield (@var{s}, @var{key}, @dots{}) -## Extract a field from a structure (or a nested structure). For example: -## -## @example -## @group -## ss(1,2).fd(3).b = 5; -## getfield (ss, @{1,2@}, "fd", @{3@}, "b") -## @result{} 5 -## @end group -## @end example +## @deftypefn {Function File} {[@var{val}] =} getfield (@var{s}, @var{field}) +## @deftypefnx {Function File} {[@var{val}] =} getfield (@var{s}, @var{idx1}, @var{field1}, @var{idx2}, @var{field2}, @dots{}) +## Extract a field from a structure (or a nested structure). The syntax +## is the same as @code{setfield}, except it omits the final @var{val} +## argument, returning this value instead of setting it. ## -## Note that the function call in the previous example is equivalent to -## the expression -## -## @example -## @group -## i1 = @{1,2@}; i2 = "fd"; i3 = @{3@}; i4= "b"; -## ss(i1@{:@}).(i2)(i3@{:@}).(i4) -## @result{} 5 -## -## @end group -## @end example ## @seealso{setfield, rmfield, isfield, isstruct, fieldnames, struct} ## @end deftypefn diff -r f2b8f90052fd -r 808e4f13e220 scripts/miscellaneous/setfield.m --- a/scripts/miscellaneous/setfield.m Tue Nov 20 13:24:51 2012 -0500 +++ b/scripts/miscellaneous/setfield.m Tue Nov 20 16:17:01 2012 -0500 @@ -18,25 +18,80 @@ ## . ## -*- texinfo -*- -## @deftypefn {Function File} {[@var{k1}, @dots{}, @var{v1}] =} setfield (@var{s}, @var{k1}, @var{v1}, @dots{}) -## Set a field member in a (nested) structure array. For example: +## @deftypefn {Function File} {@var{s} =} setfield (@var{s}, @var{field}, @var{val}) +## @deftypefnx {Function File} {@var{s} =} setfield (@var{s}, @var{idx1}, @var{field1}, @var{idx2}, @var{field2}, @dots{}, @var{val}) +## +## Set a field member @var{field} in a structure @var{s} equal to @var{val}. For example: ## ## @example ## @group -## oo(1,1).f0 = 1; -## oo = setfield (oo, @{1,2@}, "fd", @{3@}, "b", 6); -## oo(1,2).fd(3).b == 6 -## @result{} ans = 1 +## @var{s} = struct (); +## @var{s} = setfield (@var{s}, "foo bar", 42); ## @end group ## @end example ## +## @noindent +## This is equivalent to +## +## @example +## @var{s}.("foo bar") = 42; +## @end example +## +## @noindent +## Note that ordinary structure syntax @code{@var{s}.foo bar = 42} cannot be +## used here, as the field name is not a valid Octave identifier. Using +## arbitrary strings for field name is incompatible with @sc{Matlab}, so +## this usage will warn if the @code{Octave:matlab-incompatible} warning +## is set. @xref{doc-warning_ids}. +## +## With the second calling form, set a field on a structure array, +## possibly nested, with successive nested indices @var{idx1}, +## @var{idx2}, @dots{} and fields @var{field1}, @var{field2}, @dots{} +## The indices must be cells containing the desired index at this +## nesting depth. +## +## Thus consider instead, +## +## @example +## @group +## @var{s} = struct ("baz", 42); +## setfield (@var{s}, @{1@}, "foo", @{1@}, "bar", 5) +## @result{} ans = +## scalar structure containing the fields: +## baz = 42 +## foo = +## scalar structure containing the fields: +## bar = 54 +## @end group +## @end example +## +## Here we first have an ordinary structure array with one field +## @code{baz} set to 42. Then we set another field in a nested scalar structure +## indexing with two single cells containing the unique desired indices. +## +## Finally an example with nested structure arrays, +## +## @example +## @group +## @var{sa}.foo = 1; +## @var{sa} = setfield (@var{sa}, @{2@}, "bar", @{3@}, "baz", 6); +## @var{sa}(2).bar(3) +## @result{} ans = +## scalar structure containing the fields: +## baz = 6 +## @end group +## @end example +## +## Here @var{sa} is a structure array whose field @code{fd} at elements +## 1 and 2 field is in turn +## another structure array whose third element is a structure +## ## Note that the same result as in the above example could be achieved by: ## ## @example ## @group -## i1 = @{1,2@}; i2 = "fd"; i3 = @{3@}; i4 = "b"; -## oo(i1@{:@}).(i2)(i3@{:@}).(i4) == 6 -## @result{} ans = 1 +## @var{SA}.foo = 1; +## @var{SA}(2).bar(3).baz = 6 ## @end group ## @end example ## @seealso{getfield, rmfield, isfield, isstruct, fieldnames, struct}