diff options
| author | 3gg <3gg@shellblade.net> | 2025-08-09 16:03:28 +0200 |
|---|---|---|
| committer | 3gg <3gg@shellblade.net> | 2025-08-09 16:03:28 +0200 |
| commit | 727e3c59346da4f91284b34b4c18f2e0ba155e53 (patch) | |
| tree | 807dccd5cba3c6bae2f8d0c9910157e306c6da5b /more-types/src | |
Diffstat (limited to 'more-types/src')
| -rw-r--r-- | more-types/src/types.adb | 116 |
1 files changed, 116 insertions, 0 deletions
diff --git a/more-types/src/types.adb b/more-types/src/types.adb new file mode 100644 index 0000000..4e7590f --- /dev/null +++ b/more-types/src/types.adb | |||
| @@ -0,0 +1,116 @@ | |||
| 1 | with Ada.Text_IO; use Ada.Text_IO; | ||
| 2 | |||
| 3 | procedure Types is | ||
| 4 | |||
| 5 | ----------------------------------------------------------------------------- | ||
| 6 | -- Record initialization. | ||
| 7 | ----------------------------------------------------------------------------- | ||
| 8 | procedure Test_Point is | ||
| 9 | type Point is record | ||
| 10 | X : Integer := 0; | ||
| 11 | Y : Integer := 0; | ||
| 12 | end record; | ||
| 13 | |||
| 14 | Origin_1 : Point; -- Default initialization. | ||
| 15 | Origin_2 : Point := (0, 0); -- Explicit, unnamed. | ||
| 16 | Origin_3 : Point := (X => 0, Y => 0); -- Explicit, named. | ||
| 17 | Origin_4 : Point := (X => <>, Y => <>); -- Explicit, using defaults. | ||
| 18 | Origin_5 : Point := (X | Y => 0); -- Initialize both values. | ||
| 19 | Origin_6 : Point := Point'(0,0); -- Qualified expression. | ||
| 20 | begin | ||
| 21 | Put_Line ("Origin: " & Integer'Image (Origin_5.X) & ", " | ||
| 22 | & Integer'Image (Origin_5.Y)); | ||
| 23 | end Test_Point; | ||
| 24 | |||
| 25 | ----------------------------------------------------------------------------- | ||
| 26 | -- Pointers. | ||
| 27 | ----------------------------------------------------------------------------- | ||
| 28 | procedure Test_Pointer is | ||
| 29 | type Month_Type is (Jan, Feb, Mar, Apr, May, Jun, | ||
| 30 | Jul, Aug, Sep, Oct, Nov, Dec); | ||
| 31 | |||
| 32 | type Date is record | ||
| 33 | Day : Integer range 1 .. 31; | ||
| 34 | Month : Month_Type; | ||
| 35 | Year : Integer; | ||
| 36 | end record; | ||
| 37 | |||
| 38 | -- Access types are nominally typed, not structurally typed. | ||
| 39 | -- If we "own" a type X, we typically also declare an access type named | ||
| 40 | -- X_Acc, so that there is a canonical name for the access type to X. | ||
| 41 | type Date_Acc is access Date; -- Pointer to Date type. | ||
| 42 | type Different_Date_Acc is access Date; -- Different type. | ||
| 43 | |||
| 44 | Null_Date : Date_Acc := null; | ||
| 45 | |||
| 46 | -- Allocate values of the access type using the 'new' keyword. | ||
| 47 | D : Date_Acc := new Date; | ||
| 48 | |||
| 49 | -- Constraints can be given when instantiating the type. | ||
| 50 | Buffer : access String := new String(1 .. 5); | ||
| 51 | |||
| 52 | -- We can also initialize along with the allocation. | ||
| 53 | Hello_Str : access String := new String'("Hello"); | ||
| 54 | |||
| 55 | procedure Test_Null (D : Date_Acc; Name : String) is | ||
| 56 | begin | ||
| 57 | -- Dereferencing of D happens implicitly. Here we can treat D as an | ||
| 58 | -- actual Date. | ||
| 59 | if D = null then | ||
| 60 | Put_Line (Name & " is null"); | ||
| 61 | else | ||
| 62 | Put_Line (Name & " is not null"); | ||
| 63 | end if; | ||
| 64 | end Test_Null; | ||
| 65 | |||
| 66 | begin | ||
| 67 | Test_Null (Null_Date, "Null_Date"); | ||
| 68 | Test_Null (D, "D"); | ||
| 69 | end Test_Pointer; | ||
| 70 | |||
| 71 | ----------------------------------------------------------------------------- | ||
| 72 | -- Mutually recursive types. | ||
| 73 | -- | ||
| 74 | -- Similar to C++, we can forward-declare a type to break the loop. | ||
| 75 | ----------------------------------------------------------------------------- | ||
| 76 | |||
| 77 | procedure Test_MyList is | ||
| 78 | type MyList; | ||
| 79 | type MyList_Acc is access MyList; | ||
| 80 | |||
| 81 | type MyList is record | ||
| 82 | Value : Integer := 0; | ||
| 83 | Next : MyList_Acc := null; | ||
| 84 | end record; | ||
| 85 | |||
| 86 | function Cons (X : Integer; L : MyList_Acc) return MyList_Acc is | ||
| 87 | Head : MyList_Acc := new MyList; | ||
| 88 | begin | ||
| 89 | Head.Value := X; | ||
| 90 | Head.Next := L; | ||
| 91 | return Head; | ||
| 92 | end Cons; | ||
| 93 | |||
| 94 | procedure Print_List (L : access constant MyList) is | ||
| 95 | Node : access constant MyList := L; | ||
| 96 | begin | ||
| 97 | Put ("["); | ||
| 98 | while Node /= null loop | ||
| 99 | Put (Integer'Image (Node.Value) & " "); | ||
| 100 | Node := Node.next; | ||
| 101 | end loop; | ||
| 102 | Put_Line ("]"); | ||
| 103 | end Print_List; | ||
| 104 | |||
| 105 | InitialList : MyList_Acc := new MyList'(4, null); | ||
| 106 | ModifiedList : MyList_Acc; | ||
| 107 | begin | ||
| 108 | ModifiedList := Cons (1, Cons (2, Cons (3, InitialList))); | ||
| 109 | Print_List (ModifiedList); | ||
| 110 | end Test_MyList; | ||
| 111 | |||
| 112 | begin | ||
| 113 | Test_Point; | ||
| 114 | Test_Pointer; | ||
| 115 | Test_MyList; | ||
| 116 | end Types; | ||
