Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to declare a fixed value in a record?

Tags:

delphi

I would like to know how do I declare a record, that has some fixed values. I need to send data using this pattern: Byte($FF)-Byte(0..250)-Byte(0..250). I am using record for that and I would like to have the first value of it constant, so that it can't be messed up. Such as:

TPacket = record
  InitByte: byte; // =255, constant
  FirstVal,
  SecondVal: byte;
end;
like image 937
Martin Melka Avatar asked Mar 15 '12 18:03

Martin Melka


People also ask

How do you declare a constant variable?

Variables can be declared as constants by using the “const” keyword before the datatype of the variable. The constant variables can be initialized once only. The default value of constant variables are zero. A program that demonstrates the declaration of constant variables in C using const keyword is given as follows.


2 Answers

You can't rely on a constructor because, contrary to Classes, Records are not required to use them, the default parameterless constructor being used implicitly.

But you can use a constant field:

type
  TPacket = record
   type
     TBytish = 0..250;
   const
     InitByte : Byte = 255;
   var
     FirstVal,
     SecondVal: TBytish;
  end;

Then use this as a regular Record, except that you don't have (and you can't) change the InitByte field.
FillChar preserves the constant field and behaves as expected.

procedure TForm2.FormCreate(Sender: TObject);
var
  r: TPacket;
begin
  FillChar(r, SizeOf(r), #0);
  ShowMessage(Format('InitByte = %d, FirstVal = %d, SecondVal = %d', [r.InitByte, r.FirstVal,r.SecondVal]));
  // r.InitByte := 42;  // not allowed by compiler
  // r.FirstVal := 251; // not allowed by compiler
  r.FirstVal := 1;
  r.SecondVal := 2;
  ShowMessage(Format('InitByte = %d, FirstVal = %d, SecondVal = %d', [r.InitByte, r.FirstVal,r.SecondVal]));
end;

Updated to include the nested type range 0..250

like image 155
Francesca Avatar answered Sep 28 '22 17:09

Francesca


Modern versions of Delphi allow record methods. While you can't prevent someone from changing the field you can at least initialize it properly:

type
  TPacket = record
    InitByte: byte; // =255, constant
    FirstVal,
    SecondVal: byte;
    constructor Create(val1, val2 : byte);
  end;


constructor TPacket.Create(val1, val2: byte);
begin
  InitByte := 255;
  FirstVal := val1;
  SecondVal := val2;
end;
like image 27
Mike W Avatar answered Sep 28 '22 16:09

Mike W