Jump to content
Darian Miller

Default(TMyRec) usage

Recommended Posts

Given a record with managed elements such as

  TExampleRec = Record
    Example1:Integer;
    Example2:String;
  End;

When declaring and using a local variable, do you always use Default(TExampleRec) even when you know you will be setting each field?

Procedure MyTest;
var
  x:TExampleRec;
begin
  x := Default(TExampleRec);
  x.Example1 := 202;
  x.Example2 := 'Test';
  DoSomething(x);
end;

I've been in the habit of using Default(xxx) on record initialization since it was introduced (in 2009?)   I'm wondering what others do.   Pretty much the really ancient code used record pointers and New/Dispose and I slowly moved away from that for most things.

 

Share this post


Link to post

I used Default on record maybe once or twice. On the other side I rarely have a chance to use records. Nowdays it's almost always a class I am working with. 

 

Generally speaking, when it's important for readability I do like to initialize a variable/field/record just to have a cleare code when I have to revisit it. 

  • Thanks 1

Share this post


Link to post

It depends. If I'm going to initialise every field I wouldn't default initialise. Many of my records have class methods named New that don't default initialise and assign to each field. 

 

I wouldn't want to offer blanket advice. Default initialise if you need to default initialise. 

  • Thanks 1

Share this post


Link to post

When I use records, it is exceedingly rare that they are left unfilled with actual values for very long, so I would tend NOT to initialize.

  • Thanks 1

Share this post


Link to post

Yes, I do.

I expect the compiler to optimise out unnecessary assignments.

If it's supposed to be immutable, the record will have private fields and a public constructor you will have to use.

 

Adding a new field to a record later will cause it to be uninitialised, unless you hunt down every instance in your code and add an assignment for the new field manually. Unfortunately, the Delphi compiler isn't even able to emit a warning when an uninitialised record field is used or returned.

 

program Project1;

type
	TRecord = record
		b: Byte;
	end;

	function getRecord(): TRecord;
	begin
		//
	end;

var
	r: TRecord;
begin
	r := getRecord();
	WriteLn(r.b);
	readln;
end.

 

  • Thanks 1

Share this post


Link to post
5 hours ago, Der schöne Günther said:

I expect the compiler to optimise out unnecessary assignments.

Does it do that with records?  I wasn't aware of that optimization.

Share this post


Link to post
program ExampleRec;

type
  TExampleRec = Record
    Example1:Integer;
    Example2:String;
    class operator Initialize(out Dest: TExampleRec);
  End;


class operator TExampleRec.Initialize(out Dest: TExampleRec);
begin
  Dest.Example1 := 0;
  Dest.Example2 := 'abcdef';
end;


var
  rec: TExampleRec;

begin
  writeln(rec.Example2);
  readln;
end.

I have used custom managed records recently since it attaches the initialisation code to the record itself

and when used the variable does not require explicit initialisation. 

Share this post


Link to post
13 hours ago, Der schöne Günther said:

 

I expect the compiler to optimise out unnecessary assignments

Nobody expects the Delphi compiler to optimise anything 

  • Haha 1

Share this post


Link to post

I init records where possible, just as with any variable. Fields tend to be added, and I was hit several times with newly added fields containing garbage.

Edited by Fr0sT.Brutal
  • Thanks 1

Share this post


Link to post

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×