Lazarus

Free Pascal => Beginners => Topic started by: Raul_ES on March 25, 2021, 01:36:45 pm

Title: Verify existence of a variable
Post by: Raul_ES on March 25, 2021, 01:36:45 pm
Hi,

I haven't been able to find a way to do this. I thought assigned(x) was the right option.

I have in this project a main form with a global variable, but other may not.

I have a set of secondary forms that MUST check if this global variable has been declared and then, will use its value. If not declared, a certain procedure o function will be executed.

any idea?

regards,

Take care friends. I hope you're all safe and healthy.
Title: Re: Verify existence of a variable
Post by: PascalDragon on March 25, 2021, 01:41:51 pm
If you need to check whether a specific identifier exists you need to use {$if declared(XXX)}. Please note that such a check would be compile time only. In general I'd suggest you to restructure your code so that you do not depend on the existence of a global variable.
Title: Re: Verify existence of a variable
Post by: egsuh on March 25, 2021, 02:13:30 pm
AFAIK variables are for human reading, and they are transformed to pointers to addresses at compile time. It should not be possible to check whether specific name is declared as variable during runtime in principle because there exist only pointers. 
Title: Re: Verify existence of a variable
Post by: engkin on March 25, 2021, 02:20:06 pm
Probably we need to hear more, but If your global variable is of type pointer or some class then yes, assigned is what you want.
Title: Re: Verify existence of a variable
Post by: wp on March 25, 2021, 02:22:24 pm
I have a set of secondary forms that MUST check if this global variable has been declared and then, will use its value. If not declared, a certain procedure o function will be executed.
You really mean "declared"? I think your program won't compile if you did not declare a required variable. You probably mean "already used". Initialize the variable with a particular value which is not used for real purposes; suppose your variable is something list FStartDate (type TDate) - initialize it to -1. Then when you access the FStartDate check for "if FStartDate <> -1 then...".
Title: Re: Verify existence of a variable
Post by: Raul_ES on April 20, 2021, 12:02:17 am
Hi, thank you all for the feedback. sorry for the delay to answer.

Yes, actually I need to check if an *undeclared* variable inside a reusable unit has been declared globaly in the main or parent unit of the application and in that case do certain things. I guess that the {$IF DECLARED x} suggested does what I was trying to ask. It's ok to be just in compile time.

Probably, as you suggested, is much better to restructure the code. In some projects I make use of that global variable, in others dont. For that reason I try to decouple dependencies between main unit an reusable ones introducing some sort of code to check the declaration of this global variable. But as you said, it would be wise to simplify and restructure code, I tend to always pick up the complex path.

The question: {IF DECLARED x} will also work when checking in compile time the declaration of a global variable in the main unit, or it only checks it in the unit where the {$if declared x} is written? I am not sure if I explain myself  clearly.

thanks,
Title: Re: Verify existence of a variable
Post by: dbannon on April 20, 2021, 01:16:37 am
Code: Pascal  [Select][+][-]
  1. unit2;
  2. ....
  3.  
  4. var
  5.    ItsBeenDeclared : boolean;
  6.  
  7. ....
  8. {IF DECLARED x}
  9. ItsBeenDeclared := True;
  10. {$endif}
  11.  
  12. If ItsBeenDeclared then DoSomeThing
  13. else DoOtherThing;

But honestly, thats pretty ugly.

Davo
Title: Re: Verify existence of a variable
Post by: PascalDragon on April 20, 2021, 09:28:55 am
The question: {IF DECLARED x} will also work when checking in compile time the declaration of a global variable in the main unit, or it only checks it in the unit where the {$if declared x} is written? I am not sure if I explain myself  clearly.

DECLARED() can only become true if the identifier is in scope using the standard Pascal scoping rules. So if you don't use a unit that identifier is not in scope. And you can't use the main program file. So in short: no, for your case it won't help you.
Title: Re: Verify existence of a variable
Post by: MarkMLl on April 20, 2021, 10:23:52 am
DECLARED() can only become true if the identifier is in scope using the standard Pascal scoping rules. So if you don't use a unit that identifier is not in scope. And you can't use the main program file. So in short: no, for your case it won't help you.

Could I double-check something there please: should declared() work correctly if checking a variable or procedure/function exposed by an imported unit, or is it strictly same-unit?

I presume that declared() is not intended to work with unit names, types and so on.

Is there any compiler-version dependency in the above?

MarkMLl
Title: Re: Verify existence of a variable
Post by: Bart on April 20, 2021, 03:06:27 pm
Could I double-check something there please: should declared() work correctly if checking a variable or procedure/function exposed by an imported unit, or is it strictly same-unit?

It works if unit is in scope.
So if unit1 has variable foo, and main uses unit1, then declared(foo) = True.

I presume that declared() is not intended to work with unit names, types and so on.

{$if declared(unit1.foo)} will not compile.

Bart
Title: Re: Verify existence of a variable
Post by: PascalDragon on April 20, 2021, 04:37:22 pm
DECLARED() can only become true if the identifier is in scope using the standard Pascal scoping rules. So if you don't use a unit that identifier is not in scope. And you can't use the main program file. So in short: no, for your case it won't help you.

Could I double-check something there please: should declared() work correctly if checking a variable or procedure/function exposed by an imported unit, or is it strictly same-unit?

The former. As said, it uses standard Pascal scoping rules.

I presume that declared() is not intended to work with unit names, types and so on.

It works with types (including generics, though without parameter names as these are not part of the name: declared(TSomeGeneric<,,>)), but not with units.

Is there any compiler-version dependency in the above?

The only one I know of is the support for generics which I added with 2.6.0 I think (though I don't remember for sure anymore).
Title: Re: Verify existence of a variable
Post by: MarkMLl on April 20, 2021, 05:07:31 pm
Thanks for those. The unit one was probably silly, although I suppose that one might realistically want to know which of a number of choices had been imported (which could obviously be controlled by a define /above/ the imports, which was also checked later).

MarkMLl
Title: Re: Verify existence of a variable
Post by: MarkMLl on April 21, 2021, 10:11:51 am
Observations without intending to be critical: playing around, I notice that if I have a unit called Python this fails:

Code: Pascal  [Select][+][-]
  1. {$if declared(LoadVarargsRoutine) }
  2.   Python.LoadVarargsRoutine('*', true); (* Try to load all varargs routines     *)
  3. {$endif }
  4.  

PythonDemo.lpr(86,5) Error: Evaluating a conditional compiling expression

while this is successful:

Code: Pascal  [Select][+][-]
  1. {$if declared(LoadVarargsRoutine) }
  2.   Python.LoadVarargsRoutine('*', true); (* Try to load all varargs routines     *)
  3. {$endif }
  4.  

If instead of being a unit Python is an instance of class TPython (contained in unit python_dynamic which has been appropriately imported) then neither of these forms works:

Code: Pascal  [Select][+][-]
  1. {$if declared(TPython.LoadVarargsRoutine) }
  2. ...
  3. {$if declared(Python.LoadVarargsRoutine) }
  4.  

I didn't much expect the last of those to work, but thought it worth checking the various possibilities.

MarkMLl






Title: Re: Verify existence of a variable
Post by: PascalDragon on April 21, 2021, 01:56:27 pm
Observations without intending to be critical: playing around, I notice that if I have a unit called Python this fails:

Code: Pascal  [Select][+][-]
  1. {$if declared(LoadVarargsRoutine) }
  2.   Python.LoadVarargsRoutine('*', true); (* Try to load all varargs routines     *)
  3. {$endif }
  4.  

PythonDemo.lpr(86,5) Error: Evaluating a conditional compiling expression

while this is successful:

Code: Pascal  [Select][+][-]
  1. {$if declared(LoadVarargsRoutine) }
  2.   Python.LoadVarargsRoutine('*', true); (* Try to load all varargs routines     *)
  3. {$endif }
  4.  

Am I blind or what is the difference between those two? :o

Anyway, can you please provide a small, self contained example that shows the problem?

If instead of being a unit Python is an instance of class TPython (contained in unit python_dynamic which has been appropriately imported) then neither of these forms works:

Code: Pascal  [Select][+][-]
  1. {$if declared(TPython.LoadVarargsRoutine) }
  2. ...
  3. {$if declared(Python.LoadVarargsRoutine) }
  4.  

I didn't much expect the last of those to work, but thought it worth checking the various possibilities.

Scoped identifiers names are not yet supported. They are somewhere on my ToDo list however as I had stumbled upon this in the past as well.
Title: Re: Verify existence of a variable
Post by: MarkMLl on April 21, 2021, 03:16:04 pm
Whoops! I /am/ sorry about that... I know how unpleasant it can be. The first should have had a unit name in it, demo attached.

(Edited since I'd screwed the attachment)

MarkMLl
TinyPortal © 2005-2018