Author |
Topic: RIGHT$() etc. with parameter side-effect (Read 424 times) |
|
tsh73
Full Member
member is offline


Gender: 
Posts: 210
|
 |
Re: RIGHT$() etc. with parameter side-effect
« Reply #4 on: Mar 24th, 2017, 9:03pm » |
|
Quote:| As a general rule it is bad practice to update global variables in a function. |
|
Huh? Where should I update them then?
But really if my code written so it depends from order of evaluation, I'm in trouble.
|
|
Logged
|
|
|
|
BrianM
New Member
member is offline


Posts: 15
|
 |
Re: RIGHT$() etc. with parameter side-effect
« Reply #5 on: Mar 24th, 2017, 9:30pm » |
|
Ideally a function should calculator a value from the given parameters and should not change anything else (see pure functions on Wikepedia). This avoids unintended side effects. If it calculates a value and performs other processes then to my mind it should not be a function but a subroutine. Obviously rules are made to be broken and there will always be instances where it is pragmatic to update global or (preferably) static variables. For example in the implementation of iterators.
I agree with you in that LB is rather bizarre in the order of evaluation of parameters.
Brian
|
|
Logged
|
|
|
|
Richard Russell
Administrator
member is offline


Posts: 1348
|
 |
Re: RIGHT$() etc. with parameter side-effect
« Reply #6 on: Mar 24th, 2017, 10:01pm » |
|
on Mar 24th, 2017, 9:03pm, tsh73 wrote:| Huh? Where should I update them then? |
|
If you want to change a 'global' variable in a function it's arguable that you should instead make it an ordinary variable and pass it as a BYREF parameter. True 'globals' should probably be reserved for constants (or at least values that are changed only in the 'main program').
But Liberty BASIC programs rarely achieve the highest standards of program design, not least because certain features of the language (such as arrays and structures always being global) make it impossible.
Richard.
|
|
|
|
BrianM
New Member
member is offline


Posts: 15
|
 |
Re: RIGHT$() etc. with parameter side-effect
« Reply #7 on: Mar 24th, 2017, 10:29pm » |
|
Quote:| If you want to change a 'global' variable in a function it's arguable that you should instead make it an ordinary variable and pass it as a BYREF parameter. |
|
I agree but beware. LB implements BYREF as a copy on entry to the sub/function and a copy back on return. It does not pass the address of the variable. Thus if you update a global variable as a parameter in a sub/function the global variable itself is not updated until the sub/function is exited. This has caught me out.
Brian
|
|
Logged
|
|
|
|
Richard Russell
Administrator
member is offline


Posts: 1348
|
 |
Re: RIGHT$() etc. with parameter side-effect
« Reply #8 on: Mar 24th, 2017, 10:51pm » |
|
on Mar 24th, 2017, 10:29pm, BrianM wrote: It wouldn't catch me out - BBC BASIC has always worked the same way and it's therefore what I expect. Mind you BBC BASIC is more honest about the terminology: it uses 'RETURN' rather than 'BYREF' to emphasise that it's not an address being passed but that the parameter is updated on return.
Richard.
|
|
Logged
|
|
|
|
Richard Russell
Administrator
member is offline


Posts: 1348
|
 |
Re: RIGHT$() etc. with parameter side-effect
« Reply #9 on: Mar 24th, 2017, 11:09pm » |
|
Not surprisingly the same thing happens if you use BYREF rather than a global:
Code: b$ = "good"
print right$(b$, four(b$))
end
function four(byref a$)
a$ = "bad"
four = 4
end function Richard.
|
|
Logged
|
|
|
|
Rod
Full Member
member is offline


Gender: 
Posts: 110
|
 |
Re: RIGHT$() etc. with parameter side-effect
« Reply #10 on: Mar 25th, 2017, 10:58am » |
|
I can't see how the right$() function can be enacted without the four() function being processed first. If that function changes either a global variable, or byref, a passed variable that will happen during the function call or on its return.
I take the point that the variable may be passed as a copy but I am not sure that a copy is passed when the variable is global in LB. However, changing the variable in the function should result in the updated variable being sliced. Just my opinion, as the code can't mean to accomplish anything else.
But as has been said, there are easier ways to trip up.
|
|
Logged
|
|
|
|
Richard Russell
Administrator
member is offline


Posts: 1348
|
 |
Re: RIGHT$() etc. with parameter side-effect
« Reply #11 on: Mar 25th, 2017, 2:09pm » |
|
on Mar 25th, 2017, 10:58am, Rod wrote:| I can't see how the right$() function can be enacted without the four() function being processed first. |
|
I'm sure nobody is suggesting otherwise: of course all parameters must be 'evaluated' (i.e. converted to a numeric or string value) before being passed to the function that needs them. That's inherent in being 'passed by value'.
The point is that they should be evaluated in a 'sensible' and 'predictable' fashion, for example consistently left-to-right. Evaluating all the 'function' parameters before any of the 'scalar' parameters, which appears to be what LB does, is unexpected and breaks the 'rule of least astonishment'.
Quote:| I am not sure that a copy is passed when the variable is global in LB. |
|
Two points to make there. Firstly whether the variable is global or not should not make any difference to the way it is passed to a function. In LB a global variable is one which is 'in scope' everywhere: both in the main program and within SUBs and FUNCTIONs. It is no less suitable as a parameter of a function than any other variable (that's not to say LB 4 doesn't treat globals differently: it does lots of peculiar things such as this bug!).
Secondly, as I demonstrated in a recent post, the problem persists in the absence of any global variables - using BYREF triggers exactly the same behavior.
One has to 'expect the unexpected' when using LB 4 because it has so many bugs and strange features. For example, also in respect of passing parameters to a function, this bug demonstrates that parameters aren't always passed 'by value' even though the documentation clearly states that they should be (in the absence of a BYREF).
If I'd realised just how much the actual behavior of LB 4 differs from what the documentation states, making it all but impossible to emulate accurately, I might not have set out to create LBB in the first place!
Richard.
|
|
Logged
|
|
|
|
|