Recent

Author Topic: Initialising a record  (Read 8739 times)

Thaddy

  • Hero Member
  • *****
  • Posts: 18729
  • To Europe: simply sell USA bonds: dollar collapses
Re: Initialising a record
« Reply #15 on: April 28, 2021, 01:07:32 pm »
NaN and Infinity are merely something every profesional programmer has to face at least once in their carreer. A deeper understanding of what those mean is therefor essential.
If Europe sells their USA bonds the USD will collapse. Europe can affort that given average state debts. The USA can't affort that. Just an advice...

winni

  • Hero Member
  • *****
  • Posts: 3197
Re: Initialising a record
« Reply #16 on: April 28, 2021, 01:14:44 pm »
Hi!

a) NaN / Nan ≠ 1

b) ∞ + 42 = ∞

Winni

PascalDragon

  • Hero Member
  • *****
  • Posts: 6311
  • Compiler Developer
Re: Initialising a record
« Reply #17 on: April 28, 2021, 01:15:33 pm »
I get the fact that compatibility with Delphi is important, but would it be sensible/possible to have an alternative to "const", say "constfix" to declare a record that really is constant, not just an initialised variable as in Delphi, and it could then be possible to write

constfix FixRec:TMyRec=(A:0;B:Nan,....
...
var LclRec:TMyRec=FixRec;

No. The compiler simply can not handle such constructs without larger rework which we are not intending to do.

A related question is that I can write

var X:double=123;
var Y:double=123;
but not
var X,Y:double=123;

The last statement seems to me completely unambiguous, and would be usefully more concise.

This is by design.

Zvoni

  • Hero Member
  • *****
  • Posts: 3242
Re: Initialising a record
« Reply #18 on: April 28, 2021, 04:06:33 pm »
I'm trying to wrap my mind around the fact, that someone wants to use a constant record.

IIRC, a constant (e.g. Const MY_USELESS_CONST:Integer = 42;) is just a symbol used in Source-code for readability, and during compilation that symbol is replaced with the actual (constant) value.

It's also the reason why it took so much time for me to get used, that in Laz/FPC we can use Constant Arrays (which, coming from a vb6-background, i couldn't understand)

So, how in the name of the holy 8 bits, is a constant record supposed to work?
Especially if you have different types for the record-members (Integers, Doubles, Strings, Woolen Socks....)

Am i wrong?!?!
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

Thaddy

  • Hero Member
  • *****
  • Posts: 18729
  • To Europe: simply sell USA bonds: dollar collapses
Re: Initialising a record
« Reply #19 on: April 28, 2021, 04:09:33 pm »
Hi!

a) NaN / Nan ≠ 1

b) ∞ + 42 = ∞

Winni
You understand it. You should name your math teacher or professor...
If Europe sells their USA bonds the USD will collapse. Europe can affort that given average state debts. The USA can't affort that. Just an advice...

lucamar

  • Hero Member
  • *****
  • Posts: 4219
Re: Initialising a record
« Reply #20 on: April 28, 2021, 04:22:05 pm »
So, how in the name of the holy 8 bits, is a constant record supposed to work?
Especially if you have different types for the record-members (Integers, Doubles, Strings, Woolen Socks....)

One way is to think of it as if it were a collection of constants with simpler types, so you have "normal" constants which are refered by names such as: Myrecord.TheString and MyRecord.WoolenSocks instead of plain TheString or WoolenSocks.

Only problem is that, unlike with simple types, the compiler doesn't (yet?) know to interpret constant records in the absence of a type so they have to be declared as typed constants which behave somewhat differently than "normal" untyped ones, hence giving rise to threads like this one. ;)
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.

Thaddy

  • Hero Member
  • *****
  • Posts: 18729
  • To Europe: simply sell USA bonds: dollar collapses
Re: Initialising a record
« Reply #21 on: April 28, 2021, 04:26:21 pm »
One way is to think of it as if it were a collection of constants with simpler types, so you have "normal" constants which are refered by names such as: Myrecord.TheString and MyRecord.WoolenSocks instead of plain TheString or WoolenSocks.
In Dutch we say Foei! You know better than that.
Although the concepts of NaN and Infinity are strange for people that are only relying on add and substract... And YOU know... ;D
If Europe sells their USA bonds the USD will collapse. Europe can affort that given average state debts. The USA can't affort that. Just an advice...

lucamar

  • Hero Member
  • *****
  • Posts: 4219
Re: Initialising a record
« Reply #22 on: April 28, 2021, 04:50:32 pm »
One way is to think of it as if it were a collection of constants with simpler types, so you have "normal" constants which are refered by names such as: Myrecord.TheString and MyRecord.WoolenSocks instead of plain TheString or WoolenSocks.
In Dutch we say Foei! You know better than that.
Although the concepts of NaN and Infinity are strange for people that are only relying on add and substract... And YOU know... ;D

I was answering (maybe badly, I admit) to Zvoni's post, where he says: "how in the name of the holy 8 bits, is a constant record supposed to work?".

Nothing to do with NaN, Infinity or the prize of sheep in Alaska ;)

Though it's very flattering that you consider that I know about those things :D
« Last Edit: April 28, 2021, 04:55:12 pm by lucamar »
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.

mtanner

  • Sr. Member
  • ****
  • Posts: 287
Re: Initialising a record
« Reply #23 on: April 28, 2021, 04:56:02 pm »
To PascalDragon.

I entirely understand the point that something on my wish-list might require a lot of work, disproportionate to any benefit. I am not in a position to judge how much work on the compiler might be required. But I asked the original question because
(a) Maybe I can code something  a better way, but don't know how to
(b) Dumb questions can be very educational
(c) From my own experience of supporting my own users, sometimes they ask for an enhancement I had not thought about, but realise I can provide it with very little effort.
(d) If you don't ask you generally don't get.

So when you say a new construct, or marginal benefit, would take a lot of effort, I appreciate the point.

I am though puzzled by your comment on
var X:double=123;
var Y:double=123;
is ok but not
var X,Y:double=123;

when it is permissible to code
var X,Y:double;

In the spirit of asking dumb questions to learn something, why is this "by design". I cannot think what sort of design consideration would lead to this restriction. Unless it is simply a TP/Delphi quirk which has to be followed for compatibility.
« Last Edit: April 28, 2021, 05:03:19 pm by mtanner »

wp

  • Hero Member
  • *****
  • Posts: 13350
Re: Initialising a record
« Reply #24 on: April 28, 2021, 04:59:15 pm »
var X,Y:double=123;
I would very much appreciate to have such a feature. The annoying hints of FPC 3.2.+ about uninitialized variables could be removed very elegantly this way.

lucamar

  • Hero Member
  • *****
  • Posts: 4219
Re: Initialising a record
« Reply #25 on: April 28, 2021, 05:09:30 pm »
I am though puzzled by your comment on
var X:double=123;
var Y:double=123;
is ok but not
var X,Y:double=123;

when it is permissible to code
var X,Y:double;

In the spirit of asking dumb questions to learn something, why is this "by design". I cannot think what sort of design consideration would lead to this restriction. Unless it is simply a TP/Delphi quirk which has to be followed for compatibility.

I'm not, by far, PascalDragon but AFAIR when this has been discussed the feel of the developers (and others) was that allowing that construction introduced some sintactic ambiguity (e.g. whether it was only Y that would end up initializad or both Y and X) that would lower the strictness of Pascal sintax.

Note, among other things, that such a sintax would allow for e.g. a long list of initialized vars, each in its own line:
Code: Pascal  [Select][+][-]
  1. var
  2. {Suppose it much longer!}
  3.   a,
  4.   b,
  5.   c,
  6.   d,
  7.   e: Integer = 0;
If you now want to discard var e or add a long comment in the middle of the list or some such operation the code might lose some clarity leading to compile- or run-time errors.

Generally speaking, it was felt that loosing the "simplicity" and strictness of Pascal for so little (perceived) advantage wasn't worth the effort.

At least that's what I understood :-[
« Last Edit: April 28, 2021, 05:11:32 pm by lucamar »
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.

mtanner

  • Sr. Member
  • ****
  • Posts: 287
Re: Initialising a record
« Reply #26 on: April 28, 2021, 05:39:00 pm »
Lucamar, Thanks for your comment.  I don't myself see any ambiguity in var X,Y:double=123; But maybe I'm biased by my experience a long time ago with IBM's PL/I. A good language in it's day, although it had the unfortunate feauture of the opposite of strict data-typing. You could try and assign any variable type to any other variable type, and PL/I would try and find a built-in coversion routine.  I think this may have been the influence of COBOL (one of the few languages I have never used much), since PL/I was designed to combine the features of COBOL, Fortran, and Algol I think. I found the advent of strict data typing in Turbo Pascal a great advantage, since it basically turned run-time bugs into compile-time messages.

Anyway, enough history, but PL/I did, as far as I recall, allow

Declare X,Y:float=123;

and also

X,Y,Z:=0;  meaning that all three variables are assigned the value 0;

I never found any ambiguity in these constructs.
« Last Edit: April 28, 2021, 05:41:24 pm by mtanner »

speter

  • Sr. Member
  • ****
  • Posts: 487
Re: Initialising a record
« Reply #27 on: April 29, 2021, 01:20:11 am »
Maybe the following could work (as being less ambiguous):
Code: Pascal  [Select][+][-]
  1. var
  2.   a = b = c : double = 123;

cheers
S.
I climbed mighty mountains, and saw that they were actually tiny foothills. :)

mtanner

  • Sr. Member
  • ****
  • Posts: 287
Re: Initialising a record
« Reply #28 on: April 29, 2021, 08:48:47 am »
speter, Not too keen on that notation.
Everyone seems content that
var X,Y,Z:double;
means the variables X,Y,Z denote double values. The description after the colon is applied to the list before the colon.  So
var X,Y,Z:double=123;
should be interpreted in the same way, the description after the colon applies to the preceeding list. It's very similar to arithmetic operator precedence, the "," forming the list has greater precedence" than the ":".

PascalDragon

  • Hero Member
  • *****
  • Posts: 6311
  • Compiler Developer
Re: Initialising a record
« Reply #29 on: April 29, 2021, 09:12:34 am »
I'm trying to wrap my mind around the fact, that someone wants to use a constant record.

Why not?

Code: Pascal  [Select][+][-]
  1. const
  2.   NullPoint: TPoint = (x: 0; y: 0);

IIRC, a constant (e.g. Const MY_USELESS_CONST:Integer = 42;) is just a symbol used in Source-code for readability, and during compilation that symbol is replaced with the actual (constant) value.

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.

So, how in the name of the holy 8 bits, is a constant record supposed to work?
Especially if you have different types for the record-members (Integers, Doubles, Strings, Woolen Socks....)

Code: Pascal  [Select][+][-]
  1. type
  2.   TWoolType = (
  3.     Sheep,
  4.     Cotton,  
  5.     Bambus
  6.   );
  7.  
  8.   TWoolenSocks = record
  9.     &Type: TWoolType;
  10.     Color: TColor;
  11.   end;
  12.  
  13.   TMyRecord = record
  14.     i: Integer;
  15.     d: Double;
  16.     s: String;
  17.     w: TWoolenSocks
  18.   end;
  19.  
  20. const
  21.   MyRecord: TMyRecord = (i: 42; d: 3.141; s: 'Hello World'; w: (&Type: Bambus; Color: clRed));

I am though puzzled by your comment on
var X:double=123;
var Y:double=123;
is ok but not
var X,Y:double=123;

when it is permissible to code
var X,Y:double;

In the spirit of asking dumb questions to learn something, why is this "by design". I cannot think what sort of design consideration would lead to this restriction. Unless it is simply a TP/Delphi quirk which has to be followed for compatibility.

I'm not, by far, PascalDragon but AFAIR when this has been discussed the feel of the developers (and others) was that allowing that construction introduced some sintactic ambiguity (e.g. whether it was only Y that would end up initializad or both Y and X) that would lower the strictness of Pascal sintax.

Note, among other things, that such a sintax would allow for e.g. a long list of initialized vars, each in its own line:
Code: Pascal  [Select][+][-]
  1. var
  2. {Suppose it much longer!}
  3.   a,
  4.   b,
  5.   c,
  6.   d,
  7.   e: Integer = 0;
If you now want to discard var e or add a long comment in the middle of the list or some such operation the code might lose some clarity leading to compile- or run-time errors.

Generally speaking, it was felt that loosing the "simplicity" and strictness of Pascal for so little (perceived) advantage wasn't worth the effort.

At least that's what I understood :-[

From the compiler's point of view there is no ambiguity. Technically that functionality would be possible without much problem. But it's indeed that it could lead to obscure bugs if one needs to adjust more complex var section and forgets that there is a initialization some lines further down. Take such a section from FPC's parser for example:

Code: Pascal  [Select][+][-]
  1.          var
  2.            srsym: tsym;
  3.            srsymtable: TSymtable;
  4.            hdef: tdef;
  5.            pd: tprocdef;
  6.            orgstoredpattern,
  7.            storedpattern: string;
  8.            callflags: tcallnodeflags;
  9.            t : ttoken;
  10.            consumeid,
  11.            wasgenericdummy,
  12.            allowspecialize,
  13.            isspecialize,
  14.            unit_found, tmpgetaddr: boolean;
  15.            dummypos,
  16.            tokenpos: tfileposinfo;
  17.            spezcontext : tspecializationcontext;
  18.            cufflags : tconsume_unitsym_flags;
  19.  

If the Booleans would have e.g. = True and I miss that when adding a new Boolean variable that should be False and I also miss to initialize it (been there, done that!) the compiler will not warn that the variable is not initialized (like it would now!) and I might need to debug a while to find out what's wrong.

While one could argue that a = True is harder to miss in e.g. an IDE that does nice highlighting of things there is also the possibility that it's less obvious if macros come into play:

Code: Pascal  [Select][+][-]
  1. {$define IsTrue := = True}
  2.  
  3. var
  4.   Foo: Boolean IsTrue;

 

TinyPortal © 2005-2018