help-octave
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

AW: another bug? with arrays of structures?


From: John W. Eaton
Subject: AW: another bug? with arrays of structures?
Date: Wed, 4 May 2005 11:03:23 -0400

On  3-May-2005, address@hidden wrote:

| Sorry for that, I must have mistyped something, it actually works.
| 
| But I just found out where my real problem comes from, its reloading an array 
of structs from file:
|  
| Octave 2.1.50:
| >> a(2).f=1
| a =
| {
|   f =
|   (
|     [1] = []
|     [2] = 1
|   )
| }
| 
| >> save test a
| >> clear all
| >> load test
| >> a
| a =
| {
|   f =
|   (
|     [1] = []
|     [2] = 1
|   )
| }
| 
| >> a(2)
| ans =
| {
|   f = 1
| }
| 
| >>
| 
| The same in Octave 2.1.69:
| octave:44> a(2).f=1
| a =
| {
|   f =
| 
|   (,
|     [1] = [](0x0)
|     [2] = 1
|   ,)
| 
| }
| 
| octave:45> save test a
| octave:46> clear all
| octave:47> load test
| octave:48> a
| a =
| {
|   f =
| 
|   {
|     [1,1] = [](0x0)
|     [1,2] = 1
|   }
| 
| }
| 
| octave:49> a(2)
| error: invalid vector index = 2
| octave:49>
| 
| Obviously something gets changed when reloading the array of structs from 
file, all the sudden a.f has two indices rather than just one. This also 
happens when loading the file saved with 2.1.50 into 2.1.69. 

I think the real problem is that it changed type, from a "structure
array" to a scalar structure with an field containing a cell array.
Please try the following patch.  It also fixes the code that loads
structures from the Matlab binary format files to handle N-d arrays.

Thanks,

jwe


src/ChangeLog:

2005-05-04  John W. Eaton  <address@hidden>

        * ls-mat5.cc (read_mat5_binary_element): Implement reading of N-d
        structure arrays.

        * ov-struct.cc (octave_struct::load_hdf5,
        octave_struct::load_binary, octave_struct::load_ascii): Assign
        cell_value to map slot, not octave_value containing the cell.
 

Index: src/ls-mat5.cc
===================================================================
RCS file: /cvs/octave/src/ls-mat5.cc,v
retrieving revision 1.17
diff -u -r1.17 ls-mat5.cc
--- src/ls-mat5.cc      29 Apr 2005 13:04:25 -0000      1.17
+++ src/ls-mat5.cc      4 May 2005 14:56:49 -0000
@@ -715,7 +715,6 @@
        FOUR_BYTE_INT fn_type;
        FOUR_BYTE_INT fn_len;
        FOUR_BYTE_INT field_name_length;
-       int i;
 
        // field name length subelement -- actually the maximum length
        // of a field name.  The Matlab docs promise this will always
@@ -742,7 +741,7 @@
            goto data_read_error;
          }
 
-       int n_fields = fn_len/field_name_length;
+       octave_idx_type n_fields = fn_len/field_name_length;
 
        fn_len = PAD (fn_len);
 
@@ -751,40 +750,30 @@
        if (! is.read (elname, fn_len))
          goto data_read_error;
 
-       int n;
-       if (dims(0) == 1)
-         n = dims(1);
-       else if (dims(1) == 1)
-         n = dims(0);
-       else
-         {
-           error ("load: can only handle one-dimensional structure arrays");
-           goto data_read_error;
-         }
+       std::vector<Cell> elt (n_fields);
 
-       Cell field_elts (n_fields, n);
+       for (octave_idx_type i = 0; i < n_fields; i++)
+         elt[i] = Cell (dims);
+
+       octave_idx_type n = dims.numel ();
 
        // fields subelements
-       for (int j = 0; j < n; j++)
+       for (octave_idx_type j = 0; j < n; j++)
          {
-           for (i = 0; i < n_fields; i++)
+           for (octave_idx_type i = 0; i < n_fields; i++)
              {
                octave_value fieldtc;
                read_mat5_binary_element (is, filename, swap, global, fieldtc);
-               field_elts(i,j) = fieldtc;
+               elt[i](j) = fieldtc;
              }
+
          }
 
-       for (int j = n_fields-1; j >= 0; j--)
+       for (octave_idx_type i = 0; i < n_fields; i++)
          {
-           const char *key = elname + j*field_name_length;
-
-           Cell c (dim_vector (n, 1));
-
-           for (int k = n-1; k >=0; k--)
-             c(k) = field_elts(j,k);
+           const char *key = elname + i*field_name_length;
 
-           m.assign (key, c);
+           m.assign (key, elt[i]);
          }
 
        tc = m;
Index: src/ov-struct.cc
===================================================================
RCS file: /cvs/octave/src/ov-struct.cc,v
retrieving revision 1.58
diff -u -r1.58 ov-struct.cc
--- src/ov-struct.cc    26 Apr 2005 19:24:33 -0000      1.58
+++ src/ov-struct.cc    4 May 2005 14:56:49 -0000
@@ -1026,7 +1026,15 @@
              if (!is)
                break;
 
-             m.assign (nm, t2);
+             Cell tcell = t2.cell_value ();
+
+             if (error_state)
+               {
+                 error ("load: internal error loading struct elements");
+                 return false;
+               }
+
+             m.assign (nm, tcell);
            }
 
          if (is) 
@@ -1103,7 +1111,15 @@
          if (!is)
            break;
 
-         m.assign (nm, t2);
+         Cell tcell = t2.cell_value ();
+
+         if (error_state)
+           {
+             error ("load: internal error loading struct elements");
+             return false;
+           }
+
+         m.assign (nm, tcell);
        }
 
       if (is) 
@@ -1179,7 +1195,15 @@
                                hdf5_read_next_data, &dsub)) > 0)
 #endif
     {
-      m.assign (dsub.name, dsub.tc);
+      Cell tcell = dsub.tc.cell_value ();
+
+      if (error_state)
+       {
+         error ("load: internal error loading struct elements");
+         return false;
+       }
+
+      m.assign (dsub.name, tcell);
 
       if (have_h5giterate_bug)
        current_item++;  // H5Giterate returned the last index processed



-------------------------------------------------------------
Octave is freely available under the terms of the GNU GPL.

Octave's home on the web:  http://www.octave.org
How to fund new projects:  http://www.octave.org/funding.html
Subscription information:  http://www.octave.org/archive.html
-------------------------------------------------------------



reply via email to

[Prev in Thread] Current Thread [Next in Thread]