Enumerated types and sets of - counts and loops

wildzero
wildzero used Ask the Experts™
on
:-)
Lets say I have this.

type
  TThing = (tgsOne, tgsTwo, tgsThree);
  TThings = set of TThing;

and then I do

var
  Things : TThings;
begin
  include(Things,tgsOne);

and that is all good, Things now contains tgsOne in the set.
then I do this
include(Things,tgsTwo);

now I want to know how many items are in the set.
showmessage( IntToStr(length(Things)) );
that dosn't want to work.

Also how can I loop the items in my set to see if they are in there/do stuff. Do I have to do
var
  Things : TThings;
  Thing : TThing;
begin
  include(Things,tgsOne);

  For Thing := low(TThing) to high(Thing) do
    If Thing in Things then
     //-- do something

:-)



Comment
Watch Question

Do more with

Expert Office
EXPERT OFFICE® is a registered trademark of EXPERTS EXCHANGE®
Commented:
Yes You should loop this way

Author

Commented:
What about getting a count of the number of items in the set?
developmentguruPresident
Commented:
Where you have
  //-- Do Something
put in
  Inc(Count);

There are faster ways of doing this.  The problem is that Delphi places sets in an appropriately sized container.  Your set would fit in one byte.  Bigger sets would use 2 or 4 bytes depending on what they need.  If you want a general function to count the number of elements in a set I would do something like the following pseudocode.  Passing an integer will type cast the set to an integer value which will allow it to handle all currently allowable set sizes.  If you need more speed than that you can use the same logic in assemly language.  Let me know if there are questions.
function CountSetItems(SetValue : integer) : byte;
var
  Mask, Count : integer;
 
begin
  Mask := $80000000;
  Count := 0;
  While Mask <> 0 do
    begin
      if SetValue and Mask <> 0 then
        inc(Count);
      Mask := Mask shr 1;
    end;
  Result := Count;
end;

Open in new window

Python 3 Fundamentals

This course will teach participants about installing and configuring Python, syntax, importing, statements, types, strings, booleans, files, lists, tuples, comprehensions, functions, and classes.

developmentguruPresident

Commented:
P.S.  the pseudo code I posted has the added advantage that it does not matter what type of set you pass it.  The down side is that it tests for values that cannot exist within a specific set (it is testing for all 32 possibilities - if your set only contains 3...).  It should be possible to create a function where you pass in the type of set and the value and it counts it by looping the appropriate number of times for the set.  I just don't have time to try it tonight, sorry.
Top Expert 2008

Commented:
just wondering what if you do this:
Include(Things, tgsNothing);
will Things contain any elements or will it contain nothing? ;)


sorry couldn't resist:)

ziolko.
Top Expert 2004
Commented:
a small sample

unit Unit1;

interface

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

type
  TForm1 = class(TForm)
    Button1: TButton;
    procedure Button1Click(Sender: TObject);
  private
    { Private-Deklarationen }
  public
    { Public-Deklarationen }
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

type
  TThing = (tgsOne, tgsTwo, tgsThree);
  TThings = set of TThing;


function getSetCount(aSet : TThings) : integer;
var
  i : TThing;
begin
  result := 0;
  for i := low(TThing) to high(TThing) do
  begin
    if (i in aset) then
      inc(result);
  end;
end;


procedure TForm1.Button1Click(Sender: TObject);
var
  ThingSet : TThings;
begin
  ThingSet := [tgsOne, tgsTwo];
  showmessage('Items in Set: '+inttostr(getSetCount(ThingSet)));
  ThingSet := ThingSet - [tgsOne];
  showmessage('Items in Set: '+inttostr(getSetCount(ThingSet)));
  ThingSet := ThingSet + [tgsThree];
  showmessage('Items in Set: '+inttostr(getSetCount(ThingSet)));
  ThingSet := ThingSet + [tgsOne];
  showmessage('Items in Set: '+inttostr(getSetCount(ThingSet)));
  ThingSet := [];
  showmessage('Items in Set: '+inttostr(getSetCount(ThingSet)));
end;

end.

meikl ;-)
Forced accept.

Computer101
EE Admin

Do more with

Expert Office
Submit tech questions to Ask the Experts™ at any time to receive solutions, advice, and new ideas from leading industry professionals.

Start 7-Day Free Trial