comp.lang.ada
 help / color / mirror / Atom feed
* [newbie] simple(?) data structures
@ 2004-06-12 22:23 Roland Illig
  2004-06-12 22:52 ` Frank
                   ` (7 more replies)
  0 siblings, 8 replies; 40+ messages in thread
From: Roland Illig @ 2004-06-12 22:23 UTC (permalink / raw)


Hi,

I'm doing my first steps with Ada. I tried to model a Go board and 
failed. In Java/C++, I would do it like this:

enum Stone { Empty, Black, White };

class Go_Board {
     private Stone[][] data;

     public Go_Board(int size) {
         data = new Stone[size][size];
     }
     public int getWidth() {
         return data[0].length;
     }
     public int getHeight() {
         return data.length;
     }
     public Stone getStone(int x, int y) {
         return data[y][x];
     }
}
/* EOF */

How can I do this in Ada? I already tried something with packages and 
generics, but that did not look nice. But I want it to look nice and Adaish.

Roland



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

* Re: [newbie] simple(?) data structures
  2004-06-12 22:23 [newbie] simple(?) data structures Roland Illig
@ 2004-06-12 22:52 ` Frank
  2004-06-13  0:10 ` Ludovic Brenta
                   ` (6 subsequent siblings)
  7 siblings, 0 replies; 40+ messages in thread
From: Frank @ 2004-06-12 22:52 UTC (permalink / raw)


Hi!

In http://www.adaworld.com there is a section "Learning Center", in there
there are some
tutorials. You will at least find an example in "Introduction to Ada", the
buzzword you are looking
for is "tagged" and Class Wide pramming.

Object programming in Ada is not quite as you are used to in Java/C++ with
respect to syntax.

Good luck,
Frank





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

* Re: [newbie] simple(?) data structures
  2004-06-12 22:23 [newbie] simple(?) data structures Roland Illig
  2004-06-12 22:52 ` Frank
@ 2004-06-13  0:10 ` Ludovic Brenta
  2004-06-13  3:13   ` Roland Illig
  2004-06-13  0:31 ` Jeffrey Carter
                   ` (5 subsequent siblings)
  7 siblings, 1 reply; 40+ messages in thread
From: Ludovic Brenta @ 2004-06-13  0:10 UTC (permalink / raw)


Roland Illig writes:
> I'm doing my first steps with Ada. I tried to model a Go board and
> failed. In Java/C++, I would do it like this:

[...]

> How can I do this in Ada? I already tried something with packages
> and generics, but that did not look nice. But I want it to look nice
> and Adaish.

Cool, great attitude.  Here is how I would do it, using generics like
you suggested:

generic
   Size : in Positive;
package Go_Board is
   type Width is range 1 .. Size;
   type Height is range 1 .. Size;

   type Stone is (Empty, Black, White);

   function Get_Stone (X : in Width; Y : in Height) return Stone;
   procedure Set_Stone (X : in Width; Y : in Height; S : in Stone);
private
   Board : array (Width, Height) of Stone;
end Go_Board;


Each instance of this package contains one board; thus you do not need
a constructor.  To create an instance:

with Ada.Text_IO;
with Go_Board;
procedure Test_Go_Board is
   package The_Board is new Go_Board (Size => 10);
begin
   for X in The_Board.Width loop
      for Y in The_Board.Height loop
         The_Board.Set_Stone (X, Y, The_Board.Empty);
         Ada.Text_IO.Put_Line ("Board (" & Integer'Image (X) & ", " &
                               Integer'Image (Y) & ") := " &
                               The_Board.Stone'Image
                                  (The_Board.Get_Stone (X, Y)));
       end loop;
   end loop;

   Ada.Text_IO.Put_Line ("Width of the board is " &
                         Integer'Image (The_Board.Width'Last - 
                                        The_Board.Width'First));

   Ada.Text_IO.Put_Line ("Height of the board is " &
                         Integer'Image (The_Board.Height'Last - 
                                        The_Board.Height'First));
end Test_Go_Board;


You may also want helper functions in the package Go_Board:

   function Height return Positive is
   begin
      return Size;
   end Height;

(note that I avoided using "use Ada.Text_IO; use The_Board" because I
wanted to make things really obvious; but you may want to consider
using such use clauses if you think the code is too cluttered)

HTH

-- 
Ludovic Brenta;



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

* Re: [newbie] simple(?) data structures
  2004-06-12 22:23 [newbie] simple(?) data structures Roland Illig
  2004-06-12 22:52 ` Frank
  2004-06-13  0:10 ` Ludovic Brenta
@ 2004-06-13  0:31 ` Jeffrey Carter
  2004-06-13  1:26 ` tmoran
                   ` (4 subsequent siblings)
  7 siblings, 0 replies; 40+ messages in thread
From: Jeffrey Carter @ 2004-06-13  0:31 UTC (permalink / raw)


Roland Illig wrote:
> 
> I'm doing my first steps with Ada. I tried to model a Go board and 
> failed. In Java/C++, I would do it like this:

How one would do it in a C-based language is almost certainly irrelevant 
to a good implementation in Ada. If you let us know what you did in Ada, 
and how you failed, we could give you more guidance, especially if this 
is homework.

Just out of curiosity, what are calls such as Go_Board (-10) or getStone 
(-10, -7) supposed to do? Your specification does not disallow them.

I would probably do something along the lines of

package Go is
    type Intersection_Content is (Empty, Black, White);
    type Board_Size is (Nine, Thirteen, Nineteen);
    type Intersection_Num is range 1 .. 19;

    type Board is limited private;

    Invalid_Board        : exception;
    Invalid_Intersection : exception;

    procedure Create (Go_Board : out Board; Size : in Board_Size);

    function Size (Go_Board : Board) return Board_Size;
    -- Raises Invalid_Board if Go_Board has not been created.

    function Contents (Go_Board : Board;
                       Row      : Intersection_Num;
                       Column   : Intersection_Num)
    return Intersection_Content;
    -- Raises Invalid_Board if Go_Board has not been created.
    -- Raises Invalid_Intersection if Row or Column are not valid for
    --    Size (Go_Board).

    -- Possibly other operations, such as Set.
private -- Go
    ...
end Go;

-- 
Jeff Carter
"Ditto, you provincial putz?"
Blazing Saddles
86




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

* Re: [newbie] simple(?) data structures
  2004-06-12 22:23 [newbie] simple(?) data structures Roland Illig
                   ` (2 preceding siblings ...)
  2004-06-13  0:31 ` Jeffrey Carter
@ 2004-06-13  1:26 ` tmoran
  2004-06-13  2:47 ` tmoran
                   ` (3 subsequent siblings)
  7 siblings, 0 replies; 40+ messages in thread
From: tmoran @ 2004-06-13  1:26 UTC (permalink / raw)


Why so complicated?  Why not just:
  type Go_Board is array(integer range <>,integer range <>) of Stone;
  This_Board : Go_Board(1 .. 19, 1 .. 19);
  That_Board : Go_Board(1 .. 13, 1 .. 13);
then directly access the array instead of getStone, and use
This_Board'length(1) instead of getHeight and This_Board'length(2) for getWidth.



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

* Re: [newbie] simple(?) data structures
  2004-06-12 22:23 [newbie] simple(?) data structures Roland Illig
                   ` (3 preceding siblings ...)
  2004-06-13  1:26 ` tmoran
@ 2004-06-13  2:47 ` tmoran
  2004-06-13  3:53   ` Roland Illig
  2004-06-13  4:46 ` Steve
                   ` (2 subsequent siblings)
  7 siblings, 1 reply; 40+ messages in thread
From: tmoran @ 2004-06-13  2:47 UTC (permalink / raw)


Why so complicated?  Why not just:
  type Go_Board is array(integer range <>,integer range <>) of Stone;
  This_Board : Go_Board(1 .. 19, 1 .. 19);
  That_Board : Go_Board(1 .. 13, 1 .. 13);
then directly access the array instead of getStone, and use
This_Board'length(1) instead of getHeight and This_Board'length(2) for getWidth



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

* Re: [newbie] simple(?) data structures
  2004-06-13  0:10 ` Ludovic Brenta
@ 2004-06-13  3:13   ` Roland Illig
  2004-06-13  7:59     ` Marius Amado Alves
  2004-06-13 14:47     ` Stephen Leake
  0 siblings, 2 replies; 40+ messages in thread
From: Roland Illig @ 2004-06-13  3:13 UTC (permalink / raw)


Ludovic Brenta wrote:
> Cool, great attitude.  Here is how I would do it, using generics like
> you suggested:
> 
> generic
>    Size : in Positive;
> package Go_Board is
>    type Width is range 1 .. Size;
>    type Height is range 1 .. Size;
> 
>    type Stone is (Empty, Black, White);
> 
>    function Get_Stone (X : in Width; Y : in Height) return Stone;
>    procedure Set_Stone (X : in Width; Y : in Height; S : in Stone);
> private
>    Board : array (Width, Height) of Stone;
> end Go_Board;

That looks cool to me. That's exactly as I wanted it. (Burden the 
compiler with all those range checking :))

> 
> Each instance of this package contains one board; thus you do not need
> a constructor.  To create an instance:
> 
> with Ada.Text_IO;
> with Go_Board;
> procedure Test_Go_Board is
>    package The_Board is new Go_Board (Size => 10);
> begin

Many thanks for your detailed answer. Now I know what I forgot to say. 
The thing that makes the definition of the data structure that 
complicated is that I want to choose the size of the Go_Board at runtime 
and I want to pass that Go_Board to other subprograms. Is that possible 
with packages?

--   function New_Board(The_Size : Integer) return Go_Board is
--      package The_Board is new Go_Board (Size => The_Size);
--   begin
--      return The_Board;
--   end New_Board;

--   procedure Print_Board(Board : Go_Board) is
--   begin
--     null;
--   end Print_Board;

> (note that I avoided using "use Ada.Text_IO; use The_Board" because I
> wanted to make things really obvious; but you may want to consider
> using such use clauses if you think the code is too cluttered)

I like that style. It's almost equal to my own.

> HTH
It did a lot. Thanks again.

Roland



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

* Re: [newbie] simple(?) data structures
  2004-06-13  2:47 ` tmoran
@ 2004-06-13  3:53   ` Roland Illig
  2004-06-13 10:12     ` Georg Bauhaus
  0 siblings, 1 reply; 40+ messages in thread
From: Roland Illig @ 2004-06-13  3:53 UTC (permalink / raw)


tmoran@acm.org wrote:
> Why so complicated?  Why not just:
>   type Go_Board is array(integer range <>,integer range <>) of Stone;
>   This_Board : Go_Board(1 .. 19, 1 .. 19);
>   That_Board : Go_Board(1 .. 13, 1 .. 13);
> then directly access the array instead of getStone, and use
> This_Board'length(1) instead of getHeight and This_Board'length(2) for getWidth

That's too simple. :)

Seriously, I want to build abstractions using Ada, not a thin layer 
above assembly language. And perhaps I want to later extend the type. 
Maybe with a move history. And I want to guarantee that a Go_Board is 
always as wide as high.

Roland



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

* Re: [newbie] simple(?) data structures
  2004-06-12 22:23 [newbie] simple(?) data structures Roland Illig
                   ` (4 preceding siblings ...)
  2004-06-13  2:47 ` tmoran
@ 2004-06-13  4:46 ` Steve
  2004-06-13  4:59   ` tmoran
  2004-06-16 11:08 ` Roland Illig
  2004-06-24  0:09 ` Matthew Heaney
  7 siblings, 1 reply; 40+ messages in thread
From: Steve @ 2004-06-13  4:46 UTC (permalink / raw)


To me this looks like a simple dynamically sized structure.  Here is the
package spec I might use.  Note that in your example you set the x and y
sizes to the same.  For my spec I force them to the same size in the
Go_Board definition.

package Go is

  type Stone is ( Empty, Black, White );

  Max_Size : constant := 10_000;

  type Go_Range is range 1 .. Max_Size;

  type Go_Board( Go_Size : Go_Range ) is private;

  function Get_Stone( board : Go_Board; x, y : Go_Range ) return Stone;

  function Get_Size( board : Go_Board ) return Go_Range;

private
  type Go_Cells is array( Go_Range range <>, Go_Range range <> ) of Stone;

  type Go_Board( Go_Size : Go_Range ) is
    record
      data : Go_Cells( 1 .. Go_Size, 1 .. Go_Size );
    end record;

end Go;

Steve
(The Duck)

"Roland Illig" <roland.illig@gmx.de> wrote in message
news:2j1e30Fsrg8vU1@uni-berlin.de...
> Hi,
>
> I'm doing my first steps with Ada. I tried to model a Go board and
> failed. In Java/C++, I would do it like this:
>
> enum Stone { Empty, Black, White };
>
> class Go_Board {
>      private Stone[][] data;
>
>      public Go_Board(int size) {
>          data = new Stone[size][size];
>      }
>      public int getWidth() {
>          return data[0].length;
>      }
>      public int getHeight() {
>          return data.length;
>      }
>      public Stone getStone(int x, int y) {
>          return data[y][x];
>      }
> }
> /* EOF */
>
> How can I do this in Ada? I already tried something with packages and
> generics, but that did not look nice. But I want it to look nice and
Adaish.
>
> Roland





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

* Re: [newbie] simple(?) data structures
  2004-06-13  4:46 ` Steve
@ 2004-06-13  4:59   ` tmoran
  2004-06-13 17:58     ` Jeffrey Carter
  0 siblings, 1 reply; 40+ messages in thread
From: tmoran @ 2004-06-13  4:59 UTC (permalink / raw)


> type Go_Board( Go_Size : Go_Range ) is private;
But the OP now expands on his initial request with
> And perhaps I want to later extend the type. Maybe with a move history.
so he would want
  type Go_Board( Go_Size : Go_Range ) is tagged private;
to allow such additions later.



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

* Re: [newbie] simple(?) data structures
  2004-06-13  3:13   ` Roland Illig
@ 2004-06-13  7:59     ` Marius Amado Alves
  2004-06-13 11:56       ` Ludovic Brenta
  2004-06-13 14:47     ` Stephen Leake
  1 sibling, 1 reply; 40+ messages in thread
From: Marius Amado Alves @ 2004-06-13  7:59 UTC (permalink / raw)
  Cc: comp.lang.ada

> The thing that makes the definition of the data structure that 
> complicated is that I want to choose the size of the Go_Board at runtime 
> and I want to pass that Go_Board to other subprograms. Is that possible 
> with packages?
> 
> --   function New_Board(The_Size : Integer) return Go_Board is
> --      package The_Board is new Go_Board (Size => The_Size);
> --   begin
> --      return The_Board;
> --   end New_Board;

Ah, packages as first class citizens... unfortunately not Ada :-(





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

* Re: [newbie] simple(?) data structures
  2004-06-13  3:53   ` Roland Illig
@ 2004-06-13 10:12     ` Georg Bauhaus
  2004-06-13 23:32       ` Robert I. Eachus
  0 siblings, 1 reply; 40+ messages in thread
From: Georg Bauhaus @ 2004-06-13 10:12 UTC (permalink / raw)


Roland Illig <roland.illig@gmx.de> wrote:
: tmoran@acm.org wrote:
:> Why so complicated?  Why not just:
:>   type Go_Board is array(integer range <>,integer range <>) of Stone;
:>   This_Board : Go_Board(1 .. 19, 1 .. 19);
:>   That_Board : Go_Board(1 .. 13, 1 .. 13);
:> then directly access the array instead of getStone, and use
:> This_Board'length(1) instead of getHeight and This_Board'length(2) for getWidth
: 
: That's too simple. :)
: 
: Seriously, I want to build abstractions using Ada,

As has been suggested, you don't need a whole lot of language
support to build the abstraction. For example, if only the size
of the board is a variable property of a Go board (once, when a
variable of type Go_Board is declared), type extensions are not
needed, neither are generics.
When there are no other properties that need to be seen from the
outside, then with a suitably defined Board_Size index type,

   type Go_Board (rows, columns: Board_Size) is private;

   -- ... subprogram declarations of the type Go_Board

Note that rows and columns are *constants* in a discriminated subtype
once you have declared a new board,

   my_board: Go_Board(rows => 13, columns => 19);

So this is one possible equivalent of a (the outside view of)
the constructor.  No variable parts of Go_Board are exposed, quite
abstract :-) You can pass my_board around, using the Go_Board
subprograms.

You are now free to place any implementation detail in the private
part, as has been demonstrated, the Go_Board subprograms will
be able to see them.

So if, for implementation, you use a 2-dimensional
array, as in you C++ example, and as in Tom Moran's example,
you can make it a part of the full type's declaration 
in the private part, *and* you can use both rows, columns
and array attributes in the Go_Board subprograms.

Maybe, if there is are default values for rows and columns in
a Go board, you can use the like this:

package Go.Boards is

   type Go_Board
     (rows: Board_Size := 13; columns: Board_Size := 19)
   is private;

   -- ... subprogram declarations

private

  -- ... declarations of Cell, Cell_Array, etc

  type Go_Board
     (rows: Board_Size := 13; columns: Board_Size := 19)
   is record
     cells: Cell_Array(1..rows, 1..columns);
   end record;

end Go.Boards;



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

* Re: [newbie] simple(?) data structures
  2004-06-13  7:59     ` Marius Amado Alves
@ 2004-06-13 11:56       ` Ludovic Brenta
  0 siblings, 0 replies; 40+ messages in thread
From: Ludovic Brenta @ 2004-06-13 11:56 UTC (permalink / raw)


Marius Amado Alves writes:
>> The thing that makes the definition of the data structure that
>> complicated is that I want to choose the size of the Go_Board at
>> runtime and I want to pass that Go_Board to other subprograms. Is
>> that possible with packages?
>> --   function New_Board(The_Size : Integer) return Go_Board is
>> --      package The_Board is new Go_Board (Size => The_Size);
>> --   begin
>> --      return The_Board;
>> --   end New_Board;
>
> Ah, packages as first class citizens... unfortunately not Ada :-(

My generic package is elaborated at run time; this answers half of
your question.  But you cannot pass the package around, as Marius
pointed out.  To do this, you could declare a type in the generic
package, and pass instances of that type around:

generic
   Size : in Positive;
package Go_Board is
   type Width is range 1 .. Size;
   type Height is range 1 .. Size;
   type Stone is (Empty, Black, White);
   type Board is private;
   function Get_Stone (B : in Board;
                       X : in Width; Y : in Height) return Stone;
   procedure Set_Stone (B : in out Board;
                        X : in Width; Y : in Height; S : in Stone);
   procedure Copy (From : in Board; To : out Board); -- copy boards
private
   type Board is array (Width, Height) of Stone;
end Go_Board;

The potential problem with passing Boards around is that the
subprograms accepting Boards as parameters would also have to be
generic.  Ada makes it possible to pass a package as a generic
parameter.  Moreover, you can specify that the package must be an
instance of some other generic package:

generic
   with package The_Board is new Go_Board;
   -- accept board of any one size, but not of all possible sizes
procedure Fill_Empty (B : in out The_Board.Board);

Then you would instanciate like this:

with Go_Board;
with Fill_Empty;
procedure Foo is
   package Six_Board is new Go_Board (Size => 6);
   procedure Fill_Six_Board is new Fill_Board (The_Board => Six_Board);
   B : Six_Board.Board;
begin
   Fill_Six_Board (B);
end Foo;

Of course, all these subprograms could be in the package Go_Board
(like procedure Copy above), so you wouldn't have to instanciate them
separately.  Now, if you want one subprogram to accept a Board
parameter of unknown size (in a more object-oriented way), you will
need to give up static range checks, and replace them with dynamic
ones:

package Go_Board is
   type Stone is (Empty, Black, White);
   type Board is private;
   function New_Board (Size : in Positive) return Board;
   function Width (B : in Board) return Positive;
   function Height (B : in Board) return Positive;

   function Get_Stone (B : in Board;
                       X, Y : in Positive) -- no static range check
       return Stone;

   procedure Set_Stone (B : in out Board;
                        X, Y : in Positive; -- no static range check
                        S : in Stone);
private
   type Board_Array is
     array (Positive range <>, Positive range <>) of Stone;
   type Board is access Board_Array;
end Go_Board;


procedure Fill_Empty (B : in out Go_Board.Board) is
   use Go_Board;
begin
   for X in 1 .. Width (B) loop
      for Y in 1 .. Height (B) loop
         Set_Stone (B, X, Y, Empty);
      end loop;
   end loop;

   Set_Stone (B, Height (B) + 1, 1, Empty);
   -- Constraint_Error at run time: dynamic check, not static
end Fill_Empty;

HTH

-- 
Ludovic Brenta.



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

* Re: [newbie] simple(?) data structures
  2004-06-13  3:13   ` Roland Illig
  2004-06-13  7:59     ` Marius Amado Alves
@ 2004-06-13 14:47     ` Stephen Leake
  2004-06-13 18:24       ` Jeffrey Carter
  1 sibling, 1 reply; 40+ messages in thread
From: Stephen Leake @ 2004-06-13 14:47 UTC (permalink / raw)
  To: comp.lang.ada

Roland Illig <roland.illig@gmx.de> writes:

> Many thanks for your detailed answer. Now I know what I forgot to say.
> The thing that makes the definition of the data structure that
> complicated is that I want to choose the size of the Go_Board at
> runtime and I want to pass that Go_Board to other subprograms. Is that
> possible with packages?

For a run-time determined size, the answer in Ada is the same as in
C++; you need to allocate the board object after reading in the size.
However, there are two ways to do this in Ada. The most powerful is
with access types:

package Go_Board is
   type size_Type is range 10 .. 50;
   type Board_Type (size : Size_Type) is tagged limited private;
   type Board_Access_Type is access Board_Type;

   ...
end Go_Board;

with Go_Board;
with Ada.Command_Line;
procedure Go_Main
   Size : constant Go_Board.Size_Type := Go_Board.Size_Type'Value
     (Ada.Command_Line.Argument (1));

   Board : Go_Board.Board_Access_Type := new Go_Board.Board_Type (Size);
begin
   --  play go.
end Go_Main;

This will allow you to change the size again after playing one game;
deallocate Board (using an instance of Ada.Unchecked_Deallocation),
and allocate it again. Then you have to be careful not to save a copy
of the pointer to the board after the board is destroyed.

The other way is to declare the board in a local block:

with Go_Board;
with Ada.Command_Line;
procedure Go_Main
   Size : constant Go_Board.Size_Type := Go_Board.Size_Type'Value
     (Ada.Command_Line.Argument (1));

begin
   declare
       Board : Go_Board. Go_Board.Board_Type (Size);
   begin   
       --  play go.
   end;
end Go_Main;

The second way doesn't need the access type; the board is "allocated"
on the stack. But Board is only visible in the local block, which can
be a problem for some applications. And, you can't change the size
after playing one game. This might be a good way to start; learn about
access types later.

-- 
-- Stephe




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

* Re: [newbie] simple(?) data structures
  2004-06-13  4:59   ` tmoran
@ 2004-06-13 17:58     ` Jeffrey Carter
  0 siblings, 0 replies; 40+ messages in thread
From: Jeffrey Carter @ 2004-06-13 17:58 UTC (permalink / raw)


tmoran@acm.org wrote:

>>type Go_Board( Go_Size : Go_Range ) is private;
> 
> But the OP now expands on his initial request with
> 
>>And perhaps I want to later extend the type. Maybe with a move history.
> 
> so he would want
>   type Go_Board( Go_Size : Go_Range ) is tagged private;
> to allow such additions later.

I think the OP did not mean "extend" as in "type extension", but rather 
as in "add stuff to the type declaration", so using a tagged type would 
probably be overkill.

-- 
Jeff Carter
"You tiny-brained wipers of other people's bottoms!"
Monty Python & the Holy Grail
18




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

* Re: [newbie] simple(?) data structures
  2004-06-13 14:47     ` Stephen Leake
@ 2004-06-13 18:24       ` Jeffrey Carter
  0 siblings, 0 replies; 40+ messages in thread
From: Jeffrey Carter @ 2004-06-13 18:24 UTC (permalink / raw)


Stephen Leake wrote:

> For a run-time determined size, the answer in Ada is the same as in
> C++; you need to allocate the board object after reading in the size.
> However, there are two ways to do this in Ada. The most powerful is
> with access types:

As in C++, access types require manual memory management, a significant 
source of errors. Unlike C++, you don't need to use access types to 
achieve this in Ada.

> The other way is to declare the board in a local block:

This is another way, but not very flexible.

Go boards are typically 9x9, 13x13, or 19x19. Unless you're interested 
in playing around with unusual-size boards, you can achieve what you 
want by making all boards 19x19, and simply setting a field that 
indicates the actual size of the board in use. Such a board can be 
passed around, and its size changed dynamically. 19x19 is 361 bytes, 
which is unlikely to be considered "too big" on any system where the 
program is likely to run. Even if space is a consideration, each 
position only requires 2 bits, so that could be reduced to 91 bytes by 
packing.

Finally, a discriminated record with a default discriminant can (and 
should) be used to implement such a representation. Objects will be 
large enough to hold the maximum size, but the compiler will enforce 
that only the part of the board required may be accessed, and that the 
board be square. Expanding on my earlier example:

package Go is
    type Intersection_Content is (Empty, Black, White);
       -- stones are not empty; intersections are
    type Board_Size is (Nine, Thirteen, Nineteen);
    type Intersection_Num is range 1 .. 19;

    type Board is limited private;

    Invalid_Board        : exception;
    Invalid_Intersection : exception;

    procedure Create (Go_Board : out Board; Size : in Board_Size);

    function Size (Go_Board : Board) return Board_Size;
    -- Raises Invalid_Board if Go_Board has not been created.

    function Contents (Go_Board : Board;
                       Row      : Intersection_Num;
                       Column   : Intersection_Num)
    return Intersection_Content;
    -- Raises Invalid_Board if Go_Board has not been created.
    -- Raises Invalid_Intersection if Row or Column are not valid for
    --    Size (Go_Board).

    -- Possibly other operations, such as Set.
private -- Go
    type Board_Array is array
       (Intersection_Num range <>, Intersection_Num range <>) of
    Intersection_Content;
    -- 1st dimension is Row; 2nd, Column

    type Board (Size : Intersection_Num := 1) is -- 1 => not created
       Content : Board_Array (1 .. Size, 1 .. Size) :=
          (1 .. Size => (1 .. Size => Empty) );
    end record;
end Go;

Create could then be

procedure Create (Go_Board : out Board; Size : in Board_Size) is
    -- null;
begin -- Create
    case Size is
    when Nine =>
       Go_Board :=
          (Size => 9, Content => (1 .. 9 => (1 .. 9 => Empty) ) );
    when Thirteen =>
       Go_Board :=
          (Size => 13, Content => (1 .. 13 => (1 .. 13 => Empty) ) );
    when Nineteen =>
       Go_Board :=
          (Size => 19, Content => (1 .. 19 => (1 .. 19 => Empty) ) );
    end case;
end Create;

This could be relaxed to make Board non-limited, if assignment of boards 
is required, and to allow the board size to be numeric rather than an 
enumeration, if unusual-size boards are wanted.

-- 
Jeff Carter
"You tiny-brained wipers of other people's bottoms!"
Monty Python & the Holy Grail
18




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

* Re: [newbie] simple(?) data structures
  2004-06-13 10:12     ` Georg Bauhaus
@ 2004-06-13 23:32       ` Robert I. Eachus
  2004-06-14 12:29         ` Georg Bauhaus
  0 siblings, 1 reply; 40+ messages in thread
From: Robert I. Eachus @ 2004-06-13 23:32 UTC (permalink / raw)


Georg Bauhaus wrote:

> As has been suggested, you don't need a whole lot of language
> support to build the abstraction. For example, if only the size
> of the board is a variable property of a Go board (once, when a
> variable of type Go_Board is declared), type extensions are not
> needed, neither are generics.
> When there are no other properties that need to be seen from the
> outside, then with a suitably defined Board_Size index type,
> 
>    type Go_Board (rows, columns: Board_Size) is private;
> 
>    -- ... subprogram declarations of the type Go_Board...

Roland wanted the number of rows to always equal the number of columns 
so I would reccommend instead:

     type Go_Board(Size : Board_Size := 19) is private;
...
  private
     type Go_Board(Size : Board_Size := 19) is record
        Cells: Cell_Array(1..Size, 1..Size);
     end record;

-- 

                                           Robert I. Eachus

The ideology he opposed throughout his political life insisted that 
history was moved by impersonal tides and unalterable fates. Ronald 
Reagan believed instead in the courage and triumph of free men and we 
believe it all the more because we saw that courage in him.  -- George 
W. Bush June 11, 2004




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

* Re: [newbie] simple(?) data structures
  2004-06-13 23:32       ` Robert I. Eachus
@ 2004-06-14 12:29         ` Georg Bauhaus
  0 siblings, 0 replies; 40+ messages in thread
From: Georg Bauhaus @ 2004-06-14 12:29 UTC (permalink / raw)


Robert I. Eachus <rieachus@comcast.net> wrote:
: Roland wanted the number of rows to always equal the number of columns 
: so I would reccommend instead:
: 
:     type Go_Board(Size : Board_Size := 19) is private;
: ...
:  private
:     type Go_Board(Size : Board_Size := 19) is record
:        Cells: Cell_Array(1..Size, 1..Size);
:     end record;

Yes, sorry. And probably there is a better name than Cell reflecting
the positions of stones in the game.



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

* Re: [newbie] simple(?) data structures
  2004-06-12 22:23 [newbie] simple(?) data structures Roland Illig
                   ` (5 preceding siblings ...)
  2004-06-13  4:46 ` Steve
@ 2004-06-16 11:08 ` Roland Illig
  2004-06-16 21:05   ` Georg Bauhaus
  2004-06-27 13:12   ` Jacob Sparre Andersen
  2004-06-24  0:09 ` Matthew Heaney
  7 siblings, 2 replies; 40+ messages in thread
From: Roland Illig @ 2004-06-16 11:08 UTC (permalink / raw)


Roland Illig wrote:
> Hi,
> 
> I'm doing my first steps with Ada. I tried to model a Go board and 
> failed. In Java/C++, I would do it like this:
> 
> enum Stone { Empty, Black, White };
> 
> class Go_Board {
 > ...
> }
> 
> How can I do this in Ada? I already tried something with packages and 
> generics, but that did not look nice. But I want it to look nice and 
> Adaish.

Many thanks for all your help. As I'm just an Ada beginner, I'll stick 
to something simple. No packages, no inheritance. Perhaps it will evolve 
later. My first try is:

with Ada.Finalization;

package Go is

    type Stone is (Empty, Black, White);

    type Player is (Black, White);
    Other : constant array (Player) of Player := (Black => White, White 
=> Black);
    To_Stone : constant array (Player) of Stone := (Black => Black, 
White => White);

    type Move is private;
    Pass_Move : constant Move;

    type Board (Size : Positive) is private;
    function Get_Stone (The_Board : Board; X, Y : Positive) return Stone;
    procedure Do_Move (The_Board : in out Board; The_Move : in Move);
    -- ...

private

    type Move is
       record
          Pass : Boolean := False;
          X, Y : Positive;
       end record;
    Pass_Move : constant Move := (Pass => True, X => 1, Y => 1);

    type Stone_Array is array (Positive range <>, Positive range <>) of 
Stone;
    type Stone_Array_Access is access Stone_Array;
    type Board (Size : Positive) is new Ada.Finalization.Controlled with
       record
          The_Size : Natural := Size;
          Current_Player : Player := Black;
          Stones : Stone_Array_Access;
       end record;
    procedure Initialize(The_Board : in out Board);
    procedure Finalize(The_Board : in out Board);

end Go;

-- Roland



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

* Re: [newbie] simple(?) data structures
  2004-06-16 11:08 ` Roland Illig
@ 2004-06-16 21:05   ` Georg Bauhaus
  2004-06-16 23:23     ` Roland Illig
  2004-06-27 13:12   ` Jacob Sparre Andersen
  1 sibling, 1 reply; 40+ messages in thread
From: Georg Bauhaus @ 2004-06-16 21:05 UTC (permalink / raw)


Roland Illig <roland.illig@gmx.de> wrote:

:    type Stone_Array_Access is access Stone_Array;

If I understand correctly, you will have no more than
19 x 19 lines, right? So,

(a) This is a small amount of memory per board,  either "reserved"
in the program text, or allocated on the stack during a run.

(b) if you are worried about objects of this type being passed
around costly, no need :-) The compiler will make a good decision
whether to use by copy or by reference, irrespective of the
parameter mode (in, out, in out).

Any particular reason why you want to use a pointer?




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

* Re: [newbie] simple(?) data structures
  2004-06-16 21:05   ` Georg Bauhaus
@ 2004-06-16 23:23     ` Roland Illig
  2004-06-17  0:44       ` Jeffrey Carter
  0 siblings, 1 reply; 40+ messages in thread
From: Roland Illig @ 2004-06-16 23:23 UTC (permalink / raw)


Georg Bauhaus wrote:
> Roland Illig <roland.illig@gmx.de> wrote:
> 
> :    type Stone_Array_Access is access Stone_Array;
> 
> If I understand correctly, you will have no more than
> 19 x 19 lines, right? So,
> 
> [...]
 >
> Any particular reason why you want to use a pointer?

* I'm not sure what the maximum size will be.
* I've been programming in C for a long time.
* I like the controlled objects.
* It only allocates as much memory as necessary.

Well, I'm not sure if the Go_Board will ever be in action, it's just for 
learning Ada.

Roland



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

* Re: [newbie] simple(?) data structures
  2004-06-16 23:23     ` Roland Illig
@ 2004-06-17  0:44       ` Jeffrey Carter
  2004-06-17 12:37         ` Hyman Rosen
  0 siblings, 1 reply; 40+ messages in thread
From: Jeffrey Carter @ 2004-06-17  0:44 UTC (permalink / raw)


Roland Illig wrote:

> Georg Bauhaus wrote:
> 
>> Any particular reason why you want to use a pointer?
> 
> * I'm not sure what the maximum size will be.
> * I've been programming in C for a long time.
> * I like the controlled objects.
> * It only allocates as much memory as necessary.
> 
> Well, I'm not sure if the Go_Board will ever be in action, it's just for 
> learning Ada.

If you're just learning Ada, it's probably a good idea to avoid 
pointers. If you've used C a lot, it's an even better idea to avoid 
pointers, so you can learn how many situations that require pointers in 
C do not require them in Ada.

-- 
Jeff Carter
"Go and boil your bottoms."
Monty Python & the Holy Grail
01




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

* Re: [newbie] simple(?) data structures
  2004-06-17  0:44       ` Jeffrey Carter
@ 2004-06-17 12:37         ` Hyman Rosen
  2004-06-17 13:11           ` Björn Persson
                             ` (2 more replies)
  0 siblings, 3 replies; 40+ messages in thread
From: Hyman Rosen @ 2004-06-17 12:37 UTC (permalink / raw)


Jeffrey Carter wrote:
> If you've used C a lot, it's an even better idea to avoid pointers,
 > so you can learn how many situations that require pointers in  C do
 > not require them in Ada.

It would be nice if there was a tutorial explaining why this is so and
showing how to take C code with pointers and transform it into Ada code
without pointers. It's mainly about string handling, since that's where
most of C's pointer manipulation takes place. The other eliminatable
situation I can think of involves factory methods in OO when you don't
need to keep a created object around permanently, so that you can use
classwide types and return them by value. Then there's the usual bit
about stepping through an array by pointer instead of index, but that's
not a requirement in C, merely an optimization.

Do you know of any such tutorial?



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

* Re: [newbie] simple(?) data structures
  2004-06-17 12:37         ` Hyman Rosen
@ 2004-06-17 13:11           ` Björn Persson
  2004-06-18  9:55             ` Ole-Hjalmar Kristensen
  2004-06-18  0:20           ` David Starner
  2004-06-18  9:51           ` Ole-Hjalmar Kristensen
  2 siblings, 1 reply; 40+ messages in thread
From: Björn Persson @ 2004-06-17 13:11 UTC (permalink / raw)


Hyman Rosen wrote:

> It's mainly about string handling, since that's where
> most of C's pointer manipulation takes place.

And out parameters.

-- 
Björn Persson

jor ers @sv ge.
b n_p son eri nu




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

* Re: [newbie] simple(?) data structures
  2004-06-17 12:37         ` Hyman Rosen
  2004-06-17 13:11           ` Björn Persson
@ 2004-06-18  0:20           ` David Starner
  2004-06-18  5:06             ` Hyman Rosen
  2004-06-18  9:51           ` Ole-Hjalmar Kristensen
  2 siblings, 1 reply; 40+ messages in thread
From: David Starner @ 2004-06-18  0:20 UTC (permalink / raw)


On Thu, 17 Jun 2004 08:37:25 -0400, Hyman Rosen wrote:
> The usual bit
> about stepping through an array by pointer instead of index, but that's
> not a requirement in C, merely an optimization.

And not even that most of the time. Turning an index into a point has
been standard in optimizing compilers for at least a decade.



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

* Re: [newbie] simple(?) data structures
  2004-06-18  0:20           ` David Starner
@ 2004-06-18  5:06             ` Hyman Rosen
  2004-06-18  5:47               ` Martin Krischik
                                 ` (2 more replies)
  0 siblings, 3 replies; 40+ messages in thread
From: Hyman Rosen @ 2004-06-18  5:06 UTC (permalink / raw)


David Starner wrote:
> Turning an index into a point has
> been standard in optimizing compilers for at least a decade.

But if you want to call a subroutine to work on part of an array,
in C you can create a pointer into the middle of the array and
pass that, while in Ada you would need to pass both an array and
an index. That's not so easy to optimize away.



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

* Re: [newbie] simple(?) data structures
  2004-06-18  5:06             ` Hyman Rosen
@ 2004-06-18  5:47               ` Martin Krischik
  2004-06-18  7:30                 ` Brian May
                                   ` (2 more replies)
  2004-06-18 15:04               ` Georg Bauhaus
  2004-06-19  2:02               ` James Rogers
  2 siblings, 3 replies; 40+ messages in thread
From: Martin Krischik @ 2004-06-18  5:47 UTC (permalink / raw)


Hyman Rosen wrote:

> David Starner wrote:
>> Turning an index into a point has
>> been standard in optimizing compilers for at least a decade.
> 
> But if you want to call a subroutine to work on part of an array,
> in C you can create a pointer into the middle of the array and
> pass that, while in Ada you would need to pass both an array and
> an index. That's not so easy to optimize away.

I allways thought that:

My_Function (My_Data ( 20 .. Data'Last))

was the answer to that problem. And I find that a lot more elegant then a
pointer. Of corse the compiler might still us a pointer internally.

With Regards

Martin

-- 
mailto://krischik@users.sourceforge.net
http://www.ada.krischik.com




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

* Re: [newbie] simple(?) data structures
  2004-06-18  5:47               ` Martin Krischik
@ 2004-06-18  7:30                 ` Brian May
  2004-06-18 14:21                 ` Larry Kilgallen
  2004-06-19 19:51                 ` Robert I. Eachus
  2 siblings, 0 replies; 40+ messages in thread
From: Brian May @ 2004-06-18  7:30 UTC (permalink / raw)


>>>>> "Martin" == Martin Krischik <krischik@users.sourceforge.net> writes:

    >> But if you want to call a subroutine to work on part of an
    >> array, in C you can create a pointer into the middle of the
    >> array and pass that, while in Ada you would need to pass both
    >> an array and an index. That's not so easy to optimize away.

In C you would probably also need to pass a length parameter.

    Martin> I allways thought that:

    Martin> My_Function (My_Data ( 20 .. Data'Last))

    Martin> was the answer to that problem. And I find that a lot more
    Martin> elegant then a pointer. Of corse the compiler might still
    Martin> us a pointer internally.

I was going to say that ;-).
-- 
Brian May <bam@snoopy.apana.org.au>



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

* Re: [newbie] simple(?) data structures
  2004-06-17 12:37         ` Hyman Rosen
  2004-06-17 13:11           ` Björn Persson
  2004-06-18  0:20           ` David Starner
@ 2004-06-18  9:51           ` Ole-Hjalmar Kristensen
  2 siblings, 0 replies; 40+ messages in thread
From: Ole-Hjalmar Kristensen @ 2004-06-18  9:51 UTC (permalink / raw)


Hyman Rosen <hyrosen@mail.com> writes:

> Jeffrey Carter wrote:
> > If you've used C a lot, it's an even better idea to avoid pointers,
>  > so you can learn how many situations that require pointers in  C do
>  > not require them in Ada.
> 
> It would be nice if there was a tutorial explaining why this is so and
> showing how to take C code with pointers and transform it into Ada code
> without pointers. It's mainly about string handling, since that's where
> most of C's pointer manipulation takes place. The other eliminatable
> situation I can think of involves factory methods in OO when you don't
> need to keep a created object around permanently, so that you can use
> classwide types and return them by value. Then there's the usual bit
> about stepping through an array by pointer instead of index, but that's
> not a requirement in C, merely an optimization.
> 

As you probably know, using a pointer instead of an index is not
necessarily an optimization in all cases with modern compilers and
processors. As usual, it depends...

Another place where you can (usually) eliminate some pointer handling
is when returning records with variable-sized fields from functions,
like this example, snipped from real code.
Whether this method is optimal for performance I do not know, but
it surely eliminates memory (de)allocation problems.

   -- Log record header
   type Log_Record_Header is
      record
         This_Lsn         : Lsn;         -- Lsn of this record
         Prev_Lsn         : Lsn;         -- LSN of prev. record
         Time_Stamp       : Time;              -- Timestamp
         Resource_Manager : Rmid := Null_Rmid; -- Resource mgr ID
         Trans_Id         : Trid := Null_Trid; -- Transaction ID
         Tran_Prev_Lsn    : Lsn;         -- Previous lsn for this transaction
         Master_Lsn       : Lsn;         -- If chunk of log record, refers to start
         Length : Log_Buffer_Index := 0;
         Total_Length : Log_Buffer_Index := 0;
   end record;

   -- Log record, as written to file
   type Log_Record
         (N : Log_Buffer_Index) is
      record
         Log_Header : Log_Record_Header;   -- Header
                                           -- The log record contents
         Log_Body   : Log_Buffer (1 .. N);
         Next_Lsn : Lsn := (Null_Lsn); -- Set by log_read_lsn
      end record;

   -- Public interface functions

   -- Read log record with given lsn
   function Log_Read_Lsn (
                          Seq_Number :        Lsn
                         ) return  Log_Record;


> Do you know of any such tutorial?

No.

-- 
   C++: The power, elegance and simplicity of a hand grenade.



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

* Re: [newbie] simple(?) data structures
  2004-06-17 13:11           ` Björn Persson
@ 2004-06-18  9:55             ` Ole-Hjalmar Kristensen
  2004-06-18 11:03               ` Björn Persson
  2004-06-18 12:04               ` Hyman Rosen
  0 siblings, 2 replies; 40+ messages in thread
From: Ole-Hjalmar Kristensen @ 2004-06-18  9:55 UTC (permalink / raw)


Bj�rn Persson <spam-away@nowhere.nil> writes:

> Hyman Rosen wrote:
> 
> > It's mainly about string handling, since that's where
> > most of C's pointer manipulation takes place.
> 
> And out parameters.
> 
> -- 
> Bj�rn Persson
> 
> jor ers @sv ge.
> b n_p son eri nu
> 

C++ has by-reference parameter passing if you want, so you don't need
to use pointers for out parameters. However, as you cannot see from
the signature of a function (except as a comment) whether the function
modifies your parameter of not, I find this a mixed blessing.

-- 
   C++: The power, elegance and simplicity of a hand grenade.



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

* Re: [newbie] simple(?) data structures
  2004-06-18  9:55             ` Ole-Hjalmar Kristensen
@ 2004-06-18 11:03               ` Björn Persson
  2004-06-18 12:04               ` Hyman Rosen
  1 sibling, 0 replies; 40+ messages in thread
From: Björn Persson @ 2004-06-18 11:03 UTC (permalink / raw)


Ole-Hjalmar Kristensen wrote:

> Björn Persson <spam-away@nowhere.nil> writes:
> 
>>Hyman Rosen wrote:
>>
>>>It's mainly about string handling, since that's where
>>>most of C's pointer manipulation takes place.
>>
>>And out parameters.
> 
> C++ has by-reference parameter passing if you want, so you don't need
> to use pointers for out parameters.

Yes, but Hyman was talking about C.

Besides, the difference between pointers and references isn't all that big.

-- 
Björn Persson

jor ers @sv ge.
b n_p son eri nu




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

* Re: [newbie] simple(?) data structures
  2004-06-18  9:55             ` Ole-Hjalmar Kristensen
  2004-06-18 11:03               ` Björn Persson
@ 2004-06-18 12:04               ` Hyman Rosen
  2004-06-22  8:11                 ` Ole-Hjalmar Kristensen
  1 sibling, 1 reply; 40+ messages in thread
From: Hyman Rosen @ 2004-06-18 12:04 UTC (permalink / raw)


Ole-Hjalmar Kristensen wrote:
> C++ has by-reference parameter passing if you want, so you don't need
> to use pointers for out parameters. However, as you cannot see from
> the signature of a function (except as a comment) whether the function
> modifies your parameter of not, I find this a mixed blessing.

Huh? If you pass by reference in C++ you get to declare the
parameters either as plain references or as const ones. You
certainly can tell this from the signature:
     void mangle(const string &in, string &out);



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

* Re: [newbie] simple(?) data structures
  2004-06-18  5:47               ` Martin Krischik
  2004-06-18  7:30                 ` Brian May
@ 2004-06-18 14:21                 ` Larry Kilgallen
  2004-06-19 19:51                 ` Robert I. Eachus
  2 siblings, 0 replies; 40+ messages in thread
From: Larry Kilgallen @ 2004-06-18 14:21 UTC (permalink / raw)


In article <10267207.GmbXj46X37@linux1.krischik.com>, Martin Krischik <krischik@users.sourceforge.net> writes:

> I allways thought that:
> 
> My_Function (My_Data ( 20 .. Data'Last))
> 
> was the answer to that problem. And I find that a lot more elegant then a
> pointer. Of corse the compiler might still us a pointer internally.

Of course the resulting machine code (not necessarily the compiler)
internally _will_ use a pointer.  But that machine code will also
use base-2 arithmetic, without requiring the programmer to deal in
base-2.  The resulting machine code will use numeric addresses,
while letting the human programmer continue to use symbolic names
for the very same routines.

The purpose of a compiler is to make the relationship of the programmer
to the machine code more trouble-free.



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

* Re: [newbie] simple(?) data structures
  2004-06-18  5:06             ` Hyman Rosen
  2004-06-18  5:47               ` Martin Krischik
@ 2004-06-18 15:04               ` Georg Bauhaus
  2004-06-19  2:02               ` James Rogers
  2 siblings, 0 replies; 40+ messages in thread
From: Georg Bauhaus @ 2004-06-18 15:04 UTC (permalink / raw)


Hyman Rosen <hyrosen@mail.com> wrote:
 
: But if you want to call a subroutine to work on part of an array,
: in C you can create a pointer into the middle of the array and
: pass that, while in Ada you would need to pass both an array and
: an index.

While I'd do this, or pass just a String as Martin has shown, or pass
an index because the string is at the same nesting level, I can,
in Ada, create a pointer into the middle of the array and pass that,
and then use pointer arithmetic.
It is just a lot more verbose, cumbersome, and not necessary ;-)



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

* Re: [newbie] simple(?) data structures
  2004-06-18  5:06             ` Hyman Rosen
  2004-06-18  5:47               ` Martin Krischik
  2004-06-18 15:04               ` Georg Bauhaus
@ 2004-06-19  2:02               ` James Rogers
  2 siblings, 0 replies; 40+ messages in thread
From: James Rogers @ 2004-06-19  2:02 UTC (permalink / raw)


Hyman Rosen <hyrosen@mail.com> wrote in 
news:LLuAc.45601$Xw3.8597@nwrdny03.gnilink.net:

> David Starner wrote:
>> Turning an index into a point has
>> been standard in optimizing compilers for at least a decade.
> 
> But if you want to call a subroutine to work on part of an array,
> in C you can create a pointer into the middle of the array and
> pass that, while in Ada you would need to pass both an array and
> an index. That's not so easy to optimize away.
> 

I think you misunderstand Ada array slicing. Array slicing allows
you to pass only the contiguous array elements you choose to pass.
Using a C pointer to any portion of an array you are faced with
not knowing where the end of the array is. You must also pass
a second parameter indicating the number of array elements to
use starting at the address referenced by the pointer.

One of the difficulties of C array manipulation is revealed when
passing a pointer to the array as a function parameter. The
receiving function has no knowledge if the pointer actually
points to an array member. More than that, the function has no
information about the size of the array being pointed to.

When using C strings you have the null termination convention.
Unfortunately, not all C strings are automatically null terminated.
If a C string (array of char) is passed to a function using a
pointer to some element of the array, the most C string handling
functions will process bytes in memory until it encounters a value
equalling an ASCII null character. 

This kind of error is easily encountered using standard C functions
such as strcpy(). The function strcpy() copies a source string into
a target string with no concern for the size of the target string.
In fact, the value representing the target string is actually a
pointer to the target string. The function will copy values into
memory starting at the pointed-to address until it encounters a
null character in the source string. One common error is an array
bounds violation. The results of a C bounds violation are undefined.
The bounds violation will not be detected by either the strcpy()
routine, the C compiler, or the C run-time system.

Jim Rogers



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

* Re: [newbie] simple(?) data structures
  2004-06-18  5:47               ` Martin Krischik
  2004-06-18  7:30                 ` Brian May
  2004-06-18 14:21                 ` Larry Kilgallen
@ 2004-06-19 19:51                 ` Robert I. Eachus
  2 siblings, 0 replies; 40+ messages in thread
From: Robert I. Eachus @ 2004-06-19 19:51 UTC (permalink / raw)


Martin Krischik wrote:

> I allways thought that:
> 
> My_Function (My_Data ( 20 .. Data'Last))
> 
> was the answer to that problem. And I find that a lot more elegant then a
> pointer. Of corse the compiler might still us a pointer internally.

Yes, slices in Ada are the solution for one-dimensional data, which is 
by far the most common case.  However, PL/I allowed multidimensional 
slicing, and it is the one PL/I feature that I miss in Ada.  Of course, 
not many people program matrix multiplication and inversion in a way 
that requires multidimensional slicing. ;-)


-- 

                                           Robert I. Eachus

"Reason and experience both forbid us to expect that national morality 
can prevail in exclusion of religious principles." -- George Washington




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

* Re: [newbie] simple(?) data structures
  2004-06-18 12:04               ` Hyman Rosen
@ 2004-06-22  8:11                 ` Ole-Hjalmar Kristensen
  0 siblings, 0 replies; 40+ messages in thread
From: Ole-Hjalmar Kristensen @ 2004-06-22  8:11 UTC (permalink / raw)


>>>>> "HR" == Hyman Rosen <hyrosen@mail.com> writes:

    HR> Ole-Hjalmar Kristensen wrote:
    >> C++ has by-reference parameter passing if you want, so you don't need
    >> to use pointers for out parameters. However, as you cannot see from
    >> the signature of a function (except as a comment) whether the function
    >> modifies your parameter of not, I find this a mixed blessing.

    HR> Huh? If you pass by reference in C++ you get to declare the
    HR> parameters either as plain references or as const ones. You
    HR> certainly can tell this from the signature:
    HR>      void mangle(const string &in, string &out);

You are right of course. What I was really thinking of is that you
cannot see it where the function is called, something which applies to
both C++ and Ada. But modern IDE's let you jump to the definition of a
function easily, so it's not much of a problem.

-- 
   C++: The power, elegance and simplicity of a hand grenade.



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

* Re: [newbie] simple(?) data structures
  2004-06-12 22:23 [newbie] simple(?) data structures Roland Illig
                   ` (6 preceding siblings ...)
  2004-06-16 11:08 ` Roland Illig
@ 2004-06-24  0:09 ` Matthew Heaney
  2004-06-24 14:50   ` Nick Roberts
  7 siblings, 1 reply; 40+ messages in thread
From: Matthew Heaney @ 2004-06-24  0:09 UTC (permalink / raw)


Roland Illig <roland.illig@gmx.de> wrote in message news:<2j1e30Fsrg8vU1@uni-berlin.de>...
> Hi,
> 
> I'm doing my first steps with Ada. I tried to model a Go board and 
> failed. In Java/C++, I would do it like this:
> 
> enum Stone { Empty, Black, White };
> 
> class Go_Board {
>      private Stone[][] data;
> 
>      public Go_Board(int size) {
>          data = new Stone[size][size];
>      }
>      public int getWidth() {
>          return data[0].length;
>      }
>      public int getHeight() {
>          return data.length;
>      }
>      public Stone getStone(int x, int y) {
>          return data[y][x];
>      }
> }
> /* EOF */
> 
> How can I do this in Ada? I already tried something with packages and 
> generics, but that did not look nice. But I want it to look nice and Adaish.

You didn't need generics for the Java program, so therefore you don't
need them for the Ada program, either:

package Go_Boards is

   type Board_Type (Size : Positive) is private;

   type Stone_Type is (Empty, Black, White);

   function Stone (Board : Board_Type) return Stone_Type;

   --function Width (B : BT) return Positive;  --same as B.Size?

private

   type Data_Type is 
     array (Positive range <>, Positive range <>) of Stone_Type;

   type Board_Type (Size : Positive) is record
      Data : Data_Type (1 .. Size, 1 .. Size);
   end record;

end Go_Boards;


I haven't tried compiling this, but I think it should work.



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

* Re: [newbie] simple(?) data structures
  2004-06-24  0:09 ` Matthew Heaney
@ 2004-06-24 14:50   ` Nick Roberts
  0 siblings, 0 replies; 40+ messages in thread
From: Nick Roberts @ 2004-06-24 14:50 UTC (permalink / raw)


"Matthew Heaney" <mheaney@on2.com> wrote in message
news:1ec946d1.0406231609.11a051cb@posting.google.com...

> package Go_Boards is
>
>    type Board_Type (Size : Positive) is private;
>
>    type Stone_Type is (Empty, Black, White);
>
>    function Stone (Board : Board_Type) return Stone_Type;
>
>    --function Width (B : BT) return Positive;  --same as B.Size?
>
> private
>
>    type Data_Type is
>      array (Positive range <>, Positive range <>) of Stone_Type;
>
>    type Board_Type (Size : Positive) is record
>       Data : Data_Type (1 .. Size, 1 .. Size);
>    end record;
>
> end Go_Boards;

(I can't resist improving on this a tad ;-)

   package Nicks_Go is

      type Board_Size is range 7..19; -- or whatever
      type Coordinate is range 0..Board_Size'Last;

      type Go_Board (Size : Board_Size) is private;

      type Cell_Content is (Empty, Black, White);
      subtype Stone_Color is Cell_Content range Black..White;

      function Cell (
            Board : Go_Board;
            Row, Col: Coordinate) return Cell_Content;

      procedure Set_Cell (
            Board : in out Go_Board;
            Row, Col: in Coordinate;
            Cell: in Cell_Content);

   private

      type Matrix_Array is array (
            Coordinate range <>,
            Coordinate range <>) of Cell_Content;

      type Go_Board_Type (Size : Board_Size) is
         record
            Matrix: Matrix_Array(1..Size, 1..Size); -- row, col
            -- probably a lot of other stuff too
         end record;

   end Nicks_Go;

   package body Nicks_Go is

      function Cell (
            Board : Go_Board;
            Row, Col: Coordinate) return Cell_Content is
      begin
         return Board.Matrix(Row,Col);
      end;

      procedure Set_Cell (
            Board : in out Go_Board;
            Row, Col: in Coordinate;
            Cell: in Cell_Content) is
      begin
         Board.Matrix(Row,Col) := Cell;
      end;

   end Nicks_Go;

Just for fun!

-- 
Nick Roberts





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

* Re: [newbie] simple(?) data structures
  2004-06-16 11:08 ` Roland Illig
  2004-06-16 21:05   ` Georg Bauhaus
@ 2004-06-27 13:12   ` Jacob Sparre Andersen
  1 sibling, 0 replies; 40+ messages in thread
From: Jacob Sparre Andersen @ 2004-06-27 13:12 UTC (permalink / raw)


Roland Illig wrote:

>     type Stone is (Empty, Black, White);
>     type Player is (Black, White);

You might want to make Player a subtype of Stone:

      subtype Player is Stone range Black .. White;

That would remove the need for this declaration:

>     To_Stone : constant array (Player) of Stone := (Black => Black,
>     White => White);

And since the colours assigned to the players are derived from the
colours of the stones, it also makes sense from a logical point of
view.

>     type Move is private;

I would probably declare Move like this:

      type Move (Pass : Boolean := True) is
         record
            case Pass is
               when True =>
                  null;
               when False =>
                  X, Y : Positive;
            end case;
         end record;

With this construction, Move.X and Move.Y are only available if
Move.Pass is False.

And if you had used a generic package, parametrized with the size of
the board, I would definitely use the Board indexing type for Move.X
and Move.Y.

Jacob
-- 
                      CAUTION
               BLADE EXTREMELY SHARP
                KEEP OUT OF CHILDREN



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

end of thread, other threads:[~2004-06-27 13:12 UTC | newest]

Thread overview: 40+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2004-06-12 22:23 [newbie] simple(?) data structures Roland Illig
2004-06-12 22:52 ` Frank
2004-06-13  0:10 ` Ludovic Brenta
2004-06-13  3:13   ` Roland Illig
2004-06-13  7:59     ` Marius Amado Alves
2004-06-13 11:56       ` Ludovic Brenta
2004-06-13 14:47     ` Stephen Leake
2004-06-13 18:24       ` Jeffrey Carter
2004-06-13  0:31 ` Jeffrey Carter
2004-06-13  1:26 ` tmoran
2004-06-13  2:47 ` tmoran
2004-06-13  3:53   ` Roland Illig
2004-06-13 10:12     ` Georg Bauhaus
2004-06-13 23:32       ` Robert I. Eachus
2004-06-14 12:29         ` Georg Bauhaus
2004-06-13  4:46 ` Steve
2004-06-13  4:59   ` tmoran
2004-06-13 17:58     ` Jeffrey Carter
2004-06-16 11:08 ` Roland Illig
2004-06-16 21:05   ` Georg Bauhaus
2004-06-16 23:23     ` Roland Illig
2004-06-17  0:44       ` Jeffrey Carter
2004-06-17 12:37         ` Hyman Rosen
2004-06-17 13:11           ` Björn Persson
2004-06-18  9:55             ` Ole-Hjalmar Kristensen
2004-06-18 11:03               ` Björn Persson
2004-06-18 12:04               ` Hyman Rosen
2004-06-22  8:11                 ` Ole-Hjalmar Kristensen
2004-06-18  0:20           ` David Starner
2004-06-18  5:06             ` Hyman Rosen
2004-06-18  5:47               ` Martin Krischik
2004-06-18  7:30                 ` Brian May
2004-06-18 14:21                 ` Larry Kilgallen
2004-06-19 19:51                 ` Robert I. Eachus
2004-06-18 15:04               ` Georg Bauhaus
2004-06-19  2:02               ` James Rogers
2004-06-18  9:51           ` Ole-Hjalmar Kristensen
2004-06-27 13:12   ` Jacob Sparre Andersen
2004-06-24  0:09 ` Matthew Heaney
2004-06-24 14:50   ` Nick Roberts

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