comp.lang.ada
 help / color / mirror / Atom feed
* Multidimensional array vs. array of array
@ 2001-12-11 22:22 Lutz Donnerhacke
  2001-12-11 22:45 ` Mark Lundquist
  2001-12-11 23:03 ` Stephen Leake
  0 siblings, 2 replies; 9+ messages in thread
From: Lutz Donnerhacke @ 2001-12-11 22:22 UTC (permalink / raw)


How does a skilled Ada programmer define a return type containing a
multidimensional array? Of course, the simple solution works:

  type Equations is array (Rows range <>, Columns range <>) of Number;
  type Workspace (row : Rows; col : Columns) is record
    eqs : Equations (Rows'First .. row, Columns'First .. col);
    ... some more stuff ...
  end record;
  function Init_Workspace return Workspace;

But this approach fails miserably on extracting a single row from the result
as well as on construction the result in a recursive function.

I do not found a way to define this type as an array of arrays despite
writing a generic package over the maximum values:
  generic
     type Columns is range <>;
  package
     type Equation  is arry (Columns) of Number;
     type Equations is array (Rows range <>) of Equation;
     type Workspace (row : Rows) is record
        eqs : Equations (Rows'First .. row);
        ... some more stuff ...
     end record;
     function Init_Workspace return Workspace;
  end package;

But this approach does not work for a situation where determining the
resulting constraints is equivalent to simulating the Init_Workspace
recursion. This should be avoided: Error-prone, duplicated and slightly
modified code.

Any idea?



^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: Multidimensional array vs. array of array
  2001-12-11 22:22 Multidimensional array vs. array of array Lutz Donnerhacke
@ 2001-12-11 22:45 ` Mark Lundquist
  2001-12-17 15:56   ` Lutz Donnerhacke
  2001-12-11 23:03 ` Stephen Leake
  1 sibling, 1 reply; 9+ messages in thread
From: Mark Lundquist @ 2001-12-11 22:45 UTC (permalink / raw)



"Lutz Donnerhacke" <lutz@iks-jena.de> wrote in message
news:slrna1d1o8.7nl.lutz@belenus.iks-jena.de...
> How does a skilled Ada programmer define a return type containing a
> multidimensional array? Of course, the simple solution works:
>
>   type Equations is array (Rows range <>, Columns range <>) of Number;
>   type Workspace (row : Rows; col : Columns) is record
>     eqs : Equations (Rows'First .. row, Columns'First .. col);
>     ... some more stuff ...
>   end record;
>   function Init_Workspace return Workspace;
>
> But this approach fails miserably on extracting a single row from the
result
> as well as on construction the result in a recursive function.

Would it help you to just define a distinct type to represent a row in
isolation, but keep your matrix as defined above (i.e. not in terms of
composition of the row type)?

-- mark






^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: Multidimensional array vs. array of array
  2001-12-11 22:22 Multidimensional array vs. array of array Lutz Donnerhacke
  2001-12-11 22:45 ` Mark Lundquist
@ 2001-12-11 23:03 ` Stephen Leake
  2001-12-12  8:39   ` Lutz Donnerhacke
  1 sibling, 1 reply; 9+ messages in thread
From: Stephen Leake @ 2001-12-11 23:03 UTC (permalink / raw)


lutz@iks-jena.de (Lutz Donnerhacke) writes:

> How does a skilled Ada programmer define a return type containing a
> multidimensional array? 

I suspect the answer is : you don't. Define a procedure with an 'in
out' parameter instead. Or one 'in' and one 'out'.

> Of course, the simple solution works:
> 
>   type Equations is array (Rows range <>, Columns range <>) of Number;
>   type Workspace (row : Rows; col : Columns) is record
>     eqs : Equations (Rows'First .. row, Columns'First .. col);
>     ... some more stuff ...
>   end record;
>   function Init_Workspace return Workspace;
> 
> But this approach fails miserably on extracting a single row from the result
> as well as on construction the result in a recursive function.

Yes, this is a fundamental limitation. If you think about a reasonable
implementaion of multi-dimensional arrays, and what you are asking the
compiler to do, it will make sense that it is a limitation.

-- 
-- Stephe



^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: Multidimensional array vs. array of array
  2001-12-11 23:03 ` Stephen Leake
@ 2001-12-12  8:39   ` Lutz Donnerhacke
  2001-12-13  0:26     ` James Rogers
  0 siblings, 1 reply; 9+ messages in thread
From: Lutz Donnerhacke @ 2001-12-12  8:39 UTC (permalink / raw)


* Stephen Leake wrote:
>lutz@iks-jena.de (Lutz Donnerhacke) writes:
>> How does a skilled Ada programmer define a return type containing a
>> multidimensional array? 
>
>I suspect the answer is : you don't. Define a procedure with an 'in
>out' parameter instead. Or one 'in' and one 'out'.

Parameters of unconstraint type always have the constraints as in parameters.
In order to obtain the constraints from the calling procedure, you have to
return an unconstraint type.

Returning a multidimensional array is easy.
Returning an array of arrays is impossible.

A multidimensional array is often unusable in further processes. There a
array of arrays is necessary. Of course, I can use Unchecked_Conversion,
but this is not portable and not a good style.

>> But this approach fails miserably on extracting a single row from the
>> result as well as on construction the result in a recursive function.
>
>Yes, this is a fundamental limitation. If you think about a reasonable
>implementaion of multi-dimensional arrays, and what you are asking the
>compiler to do, it will make sense that it is a limitation.

I read all the discussions about Ada83/95 multidimensional arrays and know
where the limitation comes from. But I still ask: How does a skilled Ada
programmer return a array of arrays?



^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: Multidimensional array vs. array of array
  2001-12-12  8:39   ` Lutz Donnerhacke
@ 2001-12-13  0:26     ` James Rogers
  2001-12-13  9:02       ` Lutz Donnerhacke
  0 siblings, 1 reply; 9+ messages in thread
From: James Rogers @ 2001-12-13  0:26 UTC (permalink / raw)




Lutz Donnerhacke wrote:
> 
> I read all the discussions about Ada83/95 multidimensional arrays and know
> where the limitation comes from. But I still ask: How does a skilled Ada
> programmer return a array of arrays?

You can do it two different ways:

1) Put the array of arrays in a record and return the record
2) Create an access type for the array of arrays. Dynamically
   allocate the array of arrays, and return its access value.

Jim Rogers
Colorado Springs, Colorado USA



^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: Multidimensional array vs. array of array
  2001-12-13  0:26     ` James Rogers
@ 2001-12-13  9:02       ` Lutz Donnerhacke
  2001-12-13 21:49         ` Nick Roberts
  0 siblings, 1 reply; 9+ messages in thread
From: Lutz Donnerhacke @ 2001-12-13  9:02 UTC (permalink / raw)


* James Rogers wrote:
>Lutz Donnerhacke wrote:
>> I read all the discussions about Ada83/95 multidimensional arrays and know
>> where the limitation comes from. But I still ask: How does a skilled Ada
>> programmer return a array of arrays?
>
>You can do it two different ways:
>
>1) Put the array of arrays in a record and return the record

I'm unable to do this. Example?

>2) Create an access type for the array of arrays. Dynamically
>   allocate the array of arrays, and return its access value.

*gna* No way. *drawing anti-satan symbols*



^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: Multidimensional array vs. array of array
  2001-12-13  9:02       ` Lutz Donnerhacke
@ 2001-12-13 21:49         ` Nick Roberts
  2001-12-14  9:45           ` Lutz Donnerhacke
  0 siblings, 1 reply; 9+ messages in thread
From: Nick Roberts @ 2001-12-13 21:49 UTC (permalink / raw)


"Lutz Donnerhacke" <lutz@iks-jena.de> wrote in message
news:slrna1grlf.k1.lutz@taranis.iks-jena.de...

> >You can do it two different ways:
> >
> >1) Put the array of arrays in a record and return the record
>
> I'm unable to do this. Example?

I don't think this can be done.

> >2) Create an access type for the array of arrays. Dynamically
> >   allocate the array of arrays, and return its access value.
>
> *gna* No way. *drawing anti-satan symbols*

Anyway that solves nothing, in itself.

I suspect the only neat solution is for the next revision to permit
multi-dimensional slices, and a new kind of 'dimension reducing' array
conversion.

In the meantime, I can only suggest that you fudge by:

(1) using an appropriate multi-dimensional array; AND

(1a) redefine all your row/column functions so that they accept this
multidimensional array (and simply check that they have been given just one
row or column); OR

(1b) define a set of 'wrapper' functions that do this check, extract the row
or column into an appropriate array type, and then call the proper function,
perhaps doing the reverse conversion on the way back; OR

(1c) redefine all your row/column functions so that they accept this
multidimensional array plus an identification of the row/column to be
operated upon.

Horrid, yes, but I can't think of anything better. E.g.:


   type Matrix is array (Positive range <>,
                         Positive range <>) of Float;

   ...

   function Sum_Row (M: in Matrix) return Float is
      R: Float := 0.0;
   begin
      if M'Length(1) /= 1 then
         raise Constraint_Error; -- or another exception
      end if;
      for i in M'Range(2) loop
         R := R + M(M'First(1),i); -- M'First(1)=M'Last(1)=row
      end loop;
      return R;
   end;


An alternative with a wrapper function would be:


   type Vector is array (Positive range <>) of Float;

   ...

   function Sum (V: in Vector) return Float is
      R: Float := 0.0;
   begin
      for i in V'Range loop
         R := R + V(i);
      end loop;
      return R;
   end;

   ...

   function Sum_Row (M: in Matrix) return Float is
      V: Vector(M'Range(2));
   begin
      if M'Length(1) /= 1 then
         raise Constraint_Error; -- or another exception
      end if;
      for i in M'Range(2) loop
         V(i) := M'(M'First(1),i);
      end loop;
      return Sum(V);
   end;


Finally, you could pass the whole matrix (presumably this would actually be
done by reference), and simply identify the row/column to be acted upon:


   function Sum_Row (M:   in Matrix;
                     Row: in Positive) return Float is
      R: Float := 0.0;
   begin
      for i in M'Range(2) loop
         R := R + M(Row,i);
      end loop;
      return R;
   end;


It may be that the last solution, while ugly, is actually the fastest.

Does this help at all?

--
Best wishes,
Nick Roberts






^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: Multidimensional array vs. array of array
  2001-12-13 21:49         ` Nick Roberts
@ 2001-12-14  9:45           ` Lutz Donnerhacke
  0 siblings, 0 replies; 9+ messages in thread
From: Lutz Donnerhacke @ 2001-12-14  9:45 UTC (permalink / raw)


* Nick Roberts wrote:
>Does this help at all?

Yes, but I perfer a differnt approach: Returning a record containing a
multidimensional array, define an constraint array of array type from the
constraint result (ws : Workspace := Init_Workspace; type ... ws.length;),
converting (copy) the multidimensional array to a variable of the new type
and work with this new type. This is reasonable, because the following
computations are much slower, than the conversion itself.



^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: Multidimensional array vs. array of array
  2001-12-11 22:45 ` Mark Lundquist
@ 2001-12-17 15:56   ` Lutz Donnerhacke
  0 siblings, 0 replies; 9+ messages in thread
From: Lutz Donnerhacke @ 2001-12-17 15:56 UTC (permalink / raw)


* Mark Lundquist wrote:
>"Lutz Donnerhacke" <lutz@iks-jena.de> wrote in message
>> How does a skilled Ada programmer define a return type containing a
>> multidimensional array? Of course, the simple solution works:
>>
>>   type Equations is array (Rows range <>, Columns range <>) of Number;
>>   type Workspace (row : Rows; col : Columns) is record
>>     eqs : Equations (Rows'First .. row, Columns'First .. col);
>>     ... some more stuff ...
>>   end record;
>>   function Init_Workspace return Workspace;
>>
>> But this approach fails miserably on extracting a single row from the
>> result as well as on construction the result in a recursive function.
>
>Would it help you to just define a distinct type to represent a row in
>isolation, but keep your matrix as defined above (i.e. not in terms of
>composition of the row type)?

After returning the Workspace in order to define a unconstrained variables,
it is possible.



^ permalink raw reply	[flat|nested] 9+ messages in thread

end of thread, other threads:[~2001-12-17 15:56 UTC | newest]

Thread overview: 9+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2001-12-11 22:22 Multidimensional array vs. array of array Lutz Donnerhacke
2001-12-11 22:45 ` Mark Lundquist
2001-12-17 15:56   ` Lutz Donnerhacke
2001-12-11 23:03 ` Stephen Leake
2001-12-12  8:39   ` Lutz Donnerhacke
2001-12-13  0:26     ` James Rogers
2001-12-13  9:02       ` Lutz Donnerhacke
2001-12-13 21:49         ` Nick Roberts
2001-12-14  9:45           ` Lutz Donnerhacke

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox