How to print a generic type in ada?

2.9k Views Asked by At

i am currently trying to print ("Ada.Text_IO.Put") a generic type, but this always fails with errors like that:

missing argument for parameter "Item" in call to "Put" declared at a-tiinio.ads:60, instance at a-inteio.ads:18
expected type "Standard.Integer"
found private type "My_Type" defined at testtype.ads:2

These errors make sense but I dont know how to print my values. The following lines show my generic type.

generic
    type My_Type is private;
    with function "+"(Left: My_Type; Right: My_Type) return My_Type;

package TestType is
    ...
end TestType;

Thanks for any help!

2

There are 2 best solutions below

0
On BEST ANSWER

You can require another generic parameter such as the following:

with function image(Item : in My_Type) return String;

Then simply print the string output by the Image function.

An example of an actual parameter might be:

image => Integer'Image
0
On

The point of a generic being that "it" works with any type, and that of Text_IO being that it works with types known when calling its subprograms, i.e. strings, you need something else generic for printing any type. So, either pass a special function that transforms from your type to String, as answered by Jim Rogers. Or, pass a generic formal package together with My_Type, for printing. For example.

generic
    type Any_Type is private;
package Any_Type_IO is
    procedure Put (Item : Any_Type);
    procedure Get (Item : out Any_Type);
end Any_Type_IO;

with Any_Type_IO;
generic
    type My_Type is private;
    with function "+"(Left: My_Type; Right: My_Type) return My_Type;
    with package Printer is new Any_Type_Io (Any_Type => My_Type);
package TestType is
    procedure Run_Test;
end TestType;

So, together with a type to become a generic actual type of TestType, there will be a package to become a generic actual package of TestType. They match. Within an instance of TestType, you can then use them together.

type T is range 1 .. 10;
package T_IO is new Any_Type_IO (T);

package My_Test_Instance is new TestType
  (My_Type => T,
   "+"     => "+",
   Printer => T_IO);

If you provide a printing package such as Any_Type_IO, then printing becomes generic in both senses: it is the job of any matching printing package, and it must also match a generic formal package in the Ada sense.