Recent

Author Topic: Initialising a record  (Read 8555 times)

Zvoni

  • Hero Member
  • *****
  • Posts: 3226
Re: Initialising a record
« Reply #30 on: April 29, 2021, 10:09:47 am »
Code: Pascal  [Select][+][-]
  1. const
  2.   NullPoint: TPoint = (x: 0; y: 0);
OK, understood and accepted.
Quote
What you describe is only true for untyped constants, e.g. Const MY_USELESS_CONST = 42. A typed constant, like your example of const MY_USELESS_CONST: Integer = 42 is for all intents and purposes similar to a variable with the exception that you can't write to it (at least if writable consts are disabled with $J-). Such a typed constant has memory reserved in the binary's data area and you can use a pointer to it. For untyped constants that is not the case, they neither have space in the resulting binary nor can you take a pointer to them.
Just to see, if i understood it correctly:
So during "Code-Design" (don't have a better word for it) use untyped Constants for readability, since the compiler is going to replace the Symbol with the actual value (if i use the Const 259 times in my code, the compiler is going to replace the symbol with the value 259 times).
And since it's an untyped literal value you can't get a pointer to it, since you compare to the value itself instead of the value stored at some memory-address (as in a variable, or as you said: a typed constant)

Correct?
One System to rule them all, One Code to find them,
One IDE to bring them all, and to the Framework bind them,
in the Land of Redmond, where the Windows lie
---------------------------------------------------------------------
Code is like a joke: If you have to explain it, it's bad

PascalDragon

  • Hero Member
  • *****
  • Posts: 6267
  • Compiler Developer
Re: Initialising a record
« Reply #31 on: April 29, 2021, 01:22:56 pm »
Quote
What you describe is only true for untyped constants, e.g. Const MY_USELESS_CONST = 42. A typed constant, like your example of const MY_USELESS_CONST: Integer = 42 is for all intents and purposes similar to a variable with the exception that you can't write to it (at least if writable consts are disabled with $J-). Such a typed constant has memory reserved in the binary's data area and you can use a pointer to it. For untyped constants that is not the case, they neither have space in the resulting binary nor can you take a pointer to them.
Just to see, if i understood it correctly:
So during "Code-Design" (don't have a better word for it) use untyped Constants for readability, since the compiler is going to replace the Symbol with the actual value (if i use the Const 259 times in my code, the compiler is going to replace the symbol with the value 259 times).
And since it's an untyped literal value you can't get a pointer to it, since you compare to the value itself instead of the value stored at some memory-address (as in a variable, or as you said: a typed constant)

Correct?

Essentially, yes. :)

Thaddy

  • Hero Member
  • *****
  • Posts: 18676
  • Jungle wars. And failing health it seems.
Re: Initialising a record
« Reply #32 on: April 29, 2021, 01:53:13 pm »
Indeed, but also note it is much more efficient. To some this may be counter-intuitive.
Due to censorship, I changed this to "Nelly the Elephant". Keeps the message clear.

Zvoni

  • Hero Member
  • *****
  • Posts: 3226
Re: Initialising a record
« Reply #33 on: April 29, 2021, 02:03:29 pm »
OK, thx.
Which brings us back neatly to the original Post of "Constant record":
Since a record is always "typed", it basically behaves like any other variable (or in the context of the discussion: as a typed constant):
Meaning: it is (constant) "data" somewhere in memory, which has actually been allocated (contrary to untyped constant as in the discussion before).

Which brings us back to my original question: Why would someone like to have a "feature" like a constant record?
Since you don't gain anything noteworthy except maybe a "writeprotect".
Initialize that record (using Advanced Record methods --> Constructor, Default-Function), and never use it left of a ":=" (this includes passing it to a function/procedure, which does the assignment).
One System to rule them all, One Code to find them,
One IDE to bring them all, and to the Framework bind them,
in the Land of Redmond, where the Windows lie
---------------------------------------------------------------------
Code is like a joke: If you have to explain it, it's bad

PascalDragon

  • Hero Member
  • *****
  • Posts: 6267
  • Compiler Developer
Re: Initialising a record
« Reply #34 on: April 30, 2021, 09:11:07 am »
Which brings us back to my original question: Why would someone like to have a "feature" like a constant record?
Since you don't gain anything noteworthy except maybe a "writeprotect".
Initialize that record (using Advanced Record methods --> Constructor, Default-Function), and never use it left of a ":=" (this includes passing it to a function/procedure, which does the assignment).

And that write protection is the important part. Of course you could say in some comment "hey, never write to this", but what if someone does? Depending on where and how such a variable is used this could be a potential attack vector for a malicious coder or simply be a source of bugs e.g. what if my null point mentioned above is suddenly changed to (100 / - 40)?

Also, back in the Turbo Pascal days, typed constants (which were always writeable), could be used as static variables inside functions, essentially being a kind of "poor man's scoping":

Code: Pascal  [Select][+][-]
  1. {$J+}
  2.  
  3. procedure Test;
  4. const
  5.   Val: Integer = 0;
  6. begin
  7.   Writeln(Val);
  8.   Inc(Val);
  9. end;
  10.  
  11. begin
  12.   Test; // will print 0
  13.   Test; // will print 1
  14. end.

lucamar

  • Hero Member
  • *****
  • Posts: 4219
Re: Initialising a record
« Reply #35 on: April 30, 2021, 11:58:53 am »
Also, back in the Turbo Pascal days, typed constants (which were always writeable), could be used as static variables inside functions, [snip]

They can be used in exactly the same way in FPC too, in case you didn't know :-\
Turbo Pascal 3 CP/M - Amstrad PCW 8256 (512 KB !!!) :P
Lazarus/FPC 2.0.8/3.0.4 & 2.0.12/3.2.0 - 32/64 bits on:
(K|L|X)Ubuntu 12..18, Windows XP, 7, 10 and various DOSes.

PascalDragon

  • Hero Member
  • *****
  • Posts: 6267
  • Compiler Developer
Re: Initialising a record
« Reply #36 on: April 30, 2021, 03:45:48 pm »
Also, back in the Turbo Pascal days, typed constants (which were always writeable), could be used as static variables inside functions, [snip]

They can be used in exactly the same way in FPC too, in case you didn't know :-\

I probably should have mentioned that my example was done with FPC :-[

garlar27

  • Hero Member
  • *****
  • Posts: 652
Re: Initialising a record
« Reply #37 on: April 30, 2021, 05:41:18 pm »
This is not a very important question, just one of those niggling coding questions, and one which would frequently save me a line of code if I could do it.
[...]

Well I had a similar problem 9 years ago. And this is the solution:
Have you tried

Code: [Select]
procedure MyFillByte(out x;count:SizeInt;value:byte);
begin
  FillByte(x, count,value);
end;

AFAIK the "out" resets all the managed types

However if you use AllocMem, then you must (once, the first time) use the real fillbyte

I've been using that solution for almost a decade and it works like a charm.

Long story short: The problem I had initially was a memory leak when using FillByte(MyRecordVar, SizeOf(MyRecordVar)); when the record had a "string" or an "array of" field and Martin_fr gave me the perfect solution.

 

TinyPortal © 2005-2018