程序包主体和主要程序。简单分配(Ada)

我陷入了艾达。我应该创建一个具有特定Flag_Type的包,可以将其写入和读取以便打印一个简单的标记。我想以为我已经成功地使软件包广告和软件包主体adb正确了,但是我在主程序的命令上苦苦挣扎。

首先是第一,输出应该看起来像这样:

Enter the flag name: Italys flag
Enter the flag height: 2
Enter the stripes width: 3
Enter the flags colors: GWR
Italys flag
+---------+
|GGGWWWRRR|
|GGGWWWRRR|
+---------+

现在,我的包裹ADS看起来像这样:

with Ada.Text_IO; use Ada.Text_IO;
with Ada.Integer_Text_IO; use Ada.Integer_Text_IO;
with Ada.Float_Text_IO; use Ada.Float_Text_IO;

package Flagdrawer is

   type Flag_Type is private;


     procedure Get(Item: out Flag_Type);
   procedure Put(Item: in Flag_Type);

   private
   type Flag_Type is
      record

     Flag_Name: String(1..20);
     L : Integer;
     Flag_Height : Integer;
     Flag_Width : Integer;
     Flag_Colors : String(1..3);

      end record;
end Flagdrawer;

我的包体看起来像这样:

with Ada.Text_IO; use Ada.Text_IO;
with Ada.Integer_Text_IO; use Ada.Integer_Text_IO;
with Ada.Float_Text_IO; use Ada.Float_Text_IO;
with Flagdrawer; use Flagdrawer;

package body Flagdrawer is

   procedure Get(Item: out Flag_Type) is
   begin

      Get_Line(Item.Flag_Name, Item.L);
      Get(Item.Flag_Height);
      Get(Item.Flag_Width);
      Get(Item.Flag_Colors);

   end Get;

   procedure Put(Item: in Flag_Type) is

     Real_Width : Integer;

   begin
      Real_Width := Item.Flag_Width *3;
      Put(Item.Flag_Name(1..Item.L));
      New_Line;
      Put("+");
      for I in 1..Real_Width loop
     Put("-");
      end loop;
      Put_Line("+");

      for J in 1..Item.Flag_Height loop
     Put("!");
     for K in 1..Item.Flag_Width loop
        Put(Item.Flag_Colors(1));
        end loop;
        for L in 1..Item.Flag_Width loop
           Put(Item.Flag_Colors(2));
        end loop;
        for M in 1..Item.Flag_Width loop
           Put(Item.Flag_Colors(3));
        end loop;
        Put_Line("!");
      end loop;

      Put("+");
      for I in 1..Real_Width loop
     Put("-");
      end loop;
      Put_Line("+");

   end Put;

end Flagdrawer;

然后我非常缺乏的主程序如下所示:

with Ada.Text_IO; use Ada.Text_IO;
with Ada.Integer_Text_IO; use Ada.Integer_Text_IO;
with Ada.Float_Text_IO; use Ada.Float_Text_IO;
with Flagdrawer; use Flagdrawer;

procedure Tenta_Flagdrawah is

   F: Flag_Type;

begin

  Put_line("Enter the flags name (1): ");   
  Put_Line("Enter the flags height (2): ");
  Put_Line("Enter the stripes' width (3): ");
  Put_Line("Enter the RGB for the flag's colors (4): ");
  Get(F);

  New_Line;
  Put(F);

end Tenta_Flagdrawah;

Im仅用于具有特定输入的分配,可以说Get(F),其中F是Flag_Type,现在它分布在多个变量中,我不知道如何合并它们。

过去,我一直在这里得到良好的回应,有没有人可以给我一些有关Im在哪里过错的提示?我知道我的主程序严重缺乏,但我不知道如何编写它。

在此先感谢您的帮助!

编辑

我找到了一个可行的解决方案(某种程度上),该解决方案在我直接针对Simon Wright的主程序中被注释掉了,因为我没有完全理解您的声明含义。我将它们放入我的MP中,并且不断收到“项目的实际值必须是变量”。我尝试使用Item.Name代替,但是它声明了无效的前缀。你觉得我哪里出问题了?

主程序.adb

with Ada.Text_IO; use Ada.Text_IO;
with Ada.Integer_Text_IO; use Ada.Integer_Text_IO;
with Ada.Float_Text_IO; use Ada.Float_Text_IO;
with Flagdrawer; use Flagdrawer;

procedure Tenta_Flagdrawah is

   F: Flag_Type;

subtype Color_String is String (1 .. 3);

procedure Get (Item : out Flag_Type;
               Name : in String;
               Height : in Natural;
               Stripe_Width : in Natural;
               Colors : in Color_String) is
begin

      Put("Enter the flag's name: ");
      Get(Name);
      Put("Enter the flag's height: ");
      Get(Height);

   end Get;
   begin

--   Put_line("Enter the flags name (1): ");
--   Put_Line("Enter the flags height (2): ");
--   Put_Line("Enter the stripes' width (3): ");
--   Put_Line("Enter the RGB for the flag's colors (4): ");
--   Get(F);


   New_Line;
   Put(F);

end Tenta_Flagdrawah;
评论
  • gcum
    gcum 回复

    Same method as in the previous post (see here), just add the user input logic:

    main.adb

    with Ada.Text_IO; use Ada.Text_IO;
    
    procedure Main is
    
       Stripes      : constant array (Natural range <>) of Character := "GWR";
       Stripe_Width : constant Positive := 3;
    
       Width  : constant Natural := 2 + Stripes'Length * Stripe_Width;
       Height : constant Natural := 2 + 2;
    
       type Screen_X is new Natural range 0 .. Width  - 1;
       type Screen_Y is new Natural range 0 .. Height - 1;
    
       -------------
       -- Pattern --
       -------------
    
       function Pattern (X : Screen_X; Y : Screen_Y) return Character is
    
          Is_Border_LR : constant Boolean :=
            X = Screen_X'First or else X = Screen_X'Last;
    
          Is_Border_TB : constant Boolean :=
            Y = Screen_Y'First or else Y = Screen_Y'Last;
    
       begin
    
          if Is_Border_LR and Is_Border_TB then
             return '+';
          elsif Is_Border_LR then
             return '|';
          elsif Is_Border_TB then
             return '-';      
          else
             return Stripes (Integer (X - Screen_X'First - 1) / Stripe_Width);
          end if;
    
       end Pattern;
    
    begin
    
       --  The Render loop.
    
       for Y in Screen_Y loop
          for X in Screen_X loop
             Put (Pattern (X, Y));
          end loop;
          New_Line;
       end loop;
    
    end Main;
    

    输出

    $ ./main
    +---------+
    |GGGWWWRRR|
    |GGGWWWRRR|
    +---------+
    
  • 女神
    女神 回复

    A lot of your trouble is the Get procedure; it implements all the text input for the various fields without reference to whatever the main program’s doing.

    In general, it isn’t good practice to do I/O within an abstract data type like Flag; much better to do it in the calling program. (I can see that’d be awkward for Put).

    You could read the parameters in the main program and supply them to Get,

    subtype Color_String is String (1 .. 3);
    procedure Get (Item : out Flag_Type;
                   Name : in String;
                   Height : in Natural;
                   Stripe_Width : in Natural;
                   Colors : in Color_String);