unit Main;

interface

uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, StdCtrls, Generics.Collections;

type
  TForm3 = class(TForm)
    Button1: TButton;
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
    procedure ListChanged(Sender: TObject; const Item: Integer; Action: TCollectionNotification);

  public
    { Public declarations }
  end;

var
  Form3: TForm3;

implementation

{$R *.dfm}

// BeginExample: Generics_Collections_TList
// Class: Generics.Collections.TList
// Event: Generics.Collections.TList.OnNotify
// Method: Generics.Collections.TList.AddRange
// Method: Generics.Collections.TList.IndexOf
// Method: Generics.Collections.TList.LastIndexOf
// Method: Generics.Collections.TList.Contains
// Method: Generics.Collections.TList.Remove
// Method: Generics.Collections.TList.Delete
// Method: Generics.Collections.TList.DeleteRange
// Method: Generics.Collections.TList.Extract
// Method: Generics.Collections.TList.TrimExcess
// Method: Generics.Collections.TList.Clear
// Method: Generics.Collections.TList.Insert
// Method: Generics.Collections.TList.InsertRange
// Method: Generics.Collections.TList.Sort
// Method: Generics.Collections.TList.BinarySearch
// Method: Generics.Collections.TList.Reverse
// Property: Generics.Collections.TList.Count
// Property: Generics.Collections.TList.Items
// Property: Generics.Collections.TList.Capacity

// BeginCode
{
This example demonstrates the usage of the generic TList class.
}
procedure TForm3.Button1Click(Sender: TObject);
var
  List: TList<Integer>;
  FoundIndex: Integer;
begin
  { Create a new List }
  List := TList<Integer>.Create();
  { Register a notification call-back }
  List.OnNotify := ListChanged;
  { Add a few values to the list }
  List.AddRange([5, 1, 8, 2, 9, 14, 4, 5, 1]);

  MessageDlg('Index of first 1 is ' + IntToStr(List.IndexOf(1)),
    mtInformation, [mbOK], 0);
  MessageDlg('Index of last 1 is ' + IntToStr(List.LastIndexOf(1)),
    mtInformation, [mbOK], 0);
  MessageDlg('List contains elemnt 100? ' + BoolToStr(List.Contains(100)),
    mtInformation, [mbOK], 0);

  { Add another element to the list }
  List.Add(100);

  MessageDlg('There are ' + IntToStr(List.Count) + ' elements in the list.',
    mtInformation, [mbOK], 0);

  { Remove the first occurence of 1 }
  List.Remove(1);
  { Delete a few elements form position 0 }
  List.Delete(0);
  List.DeleteRange(0, 2);
  { Extract the remeining 1 from the list }
  List.Extract(1);
  { Set the capacity to the actual length }
  List.TrimExcess();
  MessageDlg('There capacity of the list is ' + IntToStr(List.Capacity),
    mtInformation, [mbOK], 0);

  { Clear the list }
  List.Clear();
  { Insert some elements }
  List.Insert(0, 2);
  List.Insert(1, 1);
  List.InsertRange(0, [6, 3, 8, 10, 11]);

  { Sort the list }
  List.Sort();

  { Binary search for the required element }
  if List.BinarySearch(6, FoundIndex) then
    MessageDlg('Found element 6 at index ' + IntToStr(FoundIndex), mtInformation, [mbOK], 0);

  { Reverse the list }
  List.Reverse();
  MessageDlg('The element on position 0 is ' + IntToStr(List.Items[0]), mtInformation, [mbOK], 0);
end;

procedure TForm3.ListChanged(Sender: TObject; const Item: Integer; Action: TCollectionNotification);
begin
  { This method is called by the List everytime a change occurs }
  if Action = cnAdded then
     MessageDlg('Element added: ' + IntToStr(Item), mtInformation, [mbOK], 0)
  else if Action = cnRemoved then
     MessageDlg('Element removed: ' + IntToStr(Item), mtInformation, [mbOK], 0)
  else if Action = cnExtracted then
     MessageDlg('Element extracted: ' + IntToStr(Item), mtInformation, [mbOK], 0)
end;
// EndCode
// EndExample: Generics_Collections_TList
end.
