package VStrings is
------------------------------------------------------------------
--| Specification for ADT to handle strings of variable length.
--| Maximum length must be at least 1.
--| Author: Michael B. Feldman, The George Washington University 
--| Last Modified: September 1995                                     
------------------------------------------------------------------
 
  type    VString(MaxLength: Positive) is private;
 
  -- exceptions

  StringOverflow   : exception;
  EmptyString      : exception;
  InvalidArguments : exception;

  -- operators

  -- constructors

  function MakeVString(S : String; MaxLength: Positive) return VString;
  -- Pre:    S and MaxLength are defined
  -- Post:   returns a VString with S as the Value part,
  --   MaxLength as the MaxLength part and S'Length as the Length part
  -- Raises: StringOverflow if S is longer than MaxLength characters

  function MakeVString(C : Character; MaxLength: Positive) return VString;
  -- Pre:    C and MaxLength are defined
  -- Post:   returns a VString with C as the Value part, Length = 1

  function EmptyVString(MaxLength: Positive) return VString;
  -- Pre:    MaxLength is defined
  -- Post:   returns a empty VString with the given MaxLength

  -- selectors

  function Length(S : VString)    return Natural;
  function MaxLength(S : VString) return Positive;
  function Value(S : VString)     return String;
  -- Pre:    S is defined
  -- Post:   returns the Length and Value of S, respectively
 
  function Head(S : VString) return Character;
  -- Pre:    S is defined
  -- Post:   returns the first character of S
  -- Raises: EmptyString if S is empty

  -- inquiry

  function IsEmpty(S : VString) return Boolean;
  -- Pre: S is defined
  -- Post: returns True if S is empty, False otherwise

  -- concatenation

  function "&" (S1, S2 : VString) return VString;
  function "&" (S1 : VString; C : Character) return VString;
  function "&" (C : Character; S1 : VString) return VString;
  function "&" (S1 : VString; S : String) return VString;
  function "&" (S : string; S1 : VString) return VString;
  -- Pre:    parameters are defined
  -- Post:   each operator returns the concatenation of its arguments;
  --   the maximum length of the result is the larger of the two
  --   maximum lengths.
  -- Raises: StringOverflow if the result would be longer than
  --   the longer of the two arguments
 
  -- lexical comparison

  function "<"  (S1, S2 : VString) return Boolean;
  function "<=" (S1, S2 : VString) return Boolean;
  function ">"  (S1, S2 : VString) return Boolean;
  function ">=" (S1, S2 : VString) return Boolean;
  -- Pre: S1 and S2 are defined
  -- Post: carries out the desired comparison, returning True or False
 
  -- search

  function Locate(Sub : VString; Within : VString) return Natural;
  function Locate(Sub : String;  Within : VString) return Natural;
  function Locate(C : Character; Within : VString) return Natural;
  -- Pre:   Sub, Within. and C are defined
  -- Post:  returns the index of the first character of Sub in Within;
  --   returns 0 if Sub is not present in Within
 
  function Tail(S : VString) return VString;
  -- Pre:    S is defined
  -- Post:   returns a string like S but with the first character removed;
  -- Raises: EmptyString if S is empty

  function Slice(S : VString; Start, Finish : Positive) return VString;
  -- Pre:    parameters are defined
  -- Post:   returns a VString whose value is
  --   the substring slice starting at position Start in S.
  --   This behaves consistently with Ada's predefined slice.
  -- Raises: InvalidParameters if Start or Finish > Length(S).
 
private

  type VString(MaxLength: Positive) is record
    CurrentLength : Natural := 0;
    StringPart : String(1 .. MaxLength) := (others => ASCII.NUL);
  end record;

end VStrings;