gil900

How the ByRef acts in this scenario?

36 posts in this topic

#1 ·  Posted (edited)

SomeFunc(Null)

Func SomeFunc(ByRef $output)
    $output = 1
EndFunc

 

Is the interpreter try to change the Null, or the interpreter know that it does not need to assign 1 to $Output ?
This code run and work.

 

Anyway if this is works why this is not working:

SomeFunc(ByRef $Output = Null)

?

I think that this is also should work.. I want to be allowed to do such thing ^

Edited by gil900

Share this post


Link to post
Share on other sites



#2 ·  Posted (edited)

Null is not a variable and (therefore) it cannot be modified, nor passed as an argument to a ByRef parameter. None of the code you posted will work. Secondly, optional ByRef parameters are certainly a useful concept but they are not currently available in AutoIt.

Edited by czardas

Share this post


Link to post
Share on other sites

#3 ·  Posted (edited)

19 minutes ago, czardas said:

Null is not a variable and (therefore) it cannot be modified, nor passed as an argument to a ByRef parameter. None of the code you posted will work. Secondly, optional ByRef parameters are certainly a useful concept but they are not currently available in AutoIt.

I know that. But it's not true that this code does not work. It compiles which is a little confusing to me..
Because it's look like it try to access data in area that does not exist.. I expected it to crash or at leas not to compile and run..
If it compile then maybe the interpreter know to not access the data at the first place in such case

Edited by gil900

Share this post


Link to post
Share on other sites

#4 ·  Posted (edited)

What have you stumbled upon? :D It's odd that it compiles and runs without crashing. I wouldn't expect that, and I have no idea what it does. It seems like a bug to me, but it could also be some kind of irrelevancy, beyond the comprehension of mere mortals such as myself. :idiot:

Edited by czardas

Share this post


Link to post
Share on other sites

#5 ·  Posted

If that knows not to access the data then it is not bug for me but only if this type of code will be also allowed:

SomeFunc(ByRef $Output = Null)

 

But that is not the case  so it is a bug for me.. it was good if it wasn't look like bug

Share this post


Link to post
Share on other sites

#6 ·  Posted

It isn't a bug, just a feature request already made.

In the meantime (iff it's ever implemented) there are two simple ways to workaround the lack of this feature.

Anyway there is no way to alter the value of a literal.


This wonderful site allows debugging and testing regular expressions (many flavors available). An absolute must have in your bookmarks.
Another excellent RegExp tutorial. Don't forget downloading your copy of up-to-date pcretest.exe and pcregrep.exe here
RegExp tutorial: enough to get started
PCRE v8.33 regexp documentation latest available release and currently implemented in AutoIt beta.

SQLitespeed is another feature-rich premier SQLite manager (includes import/export). Well worth a try.
SQLite Expert (freeware Personal Edition or payware Pro version) is a very useful SQLite database manager.
An excellent eBook covering almost every aspect of SQLite3: a must-read for anyone doing serious work.
SQL tutorial (covers "generic" SQL, but most of it applies to SQLite as well)
A work-in-progress SQLite3 tutorial. Don't miss other LxyzTHW pages!
SQLite official website with full documentation (may be newer than the SQLite library that comes standard with AutoIt)

Share this post


Link to post
Share on other sites

#7 ·  Posted (edited)

Passing a literal ByRef, compiling the code and running it without throwing an error is odd behaviour from all parties involved. I still think that it's a bug and the compiler (and the OS) ought to reject it. Optional ByRef parameters are currently a feature request - not to confuse these two separate issues. One is probably a bug and the other is potentially a missing feature.

Edited by czardas

Share this post


Link to post
Share on other sites

#8 ·  Posted

3 minutes ago, czardas said:

Passing a literal ByRef, compiling the code and running it without throwing an error is odd behaviour from all parties involved.

I don't think so but I'd like @trancexx to jump in and tell us the Truth.

Here's how I see things working. When you invoke a function with a literal as argument, say MyFunc(42), the value 42 can't be just made off thin air: it has to be implemented in a (hidden) local variable, like genuine declared user variables. The same situation occurs when you write MyFunc(40 + 2) or  ConsoleWrite("A string" & @LF & "Another one." & @LF) where the result of the add/concat has to be stored in a hidden variable.

I find it quite natural that if MyFunc is declared accepting a ByRef argument, then a reference to that hidden variable be passed.

You might say that those hidden variables could be tagged Const, in which case any attempt to change them would raise an error, but since you can't access them anyway after the callee function terminates, the point is moot.


This wonderful site allows debugging and testing regular expressions (many flavors available). An absolute must have in your bookmarks.
Another excellent RegExp tutorial. Don't forget downloading your copy of up-to-date pcretest.exe and pcregrep.exe here
RegExp tutorial: enough to get started
PCRE v8.33 regexp documentation latest available release and currently implemented in AutoIt beta.

SQLitespeed is another feature-rich premier SQLite manager (includes import/export). Well worth a try.
SQLite Expert (freeware Personal Edition or payware Pro version) is a very useful SQLite database manager.
An excellent eBook covering almost every aspect of SQLite3: a must-read for anyone doing serious work.
SQL tutorial (covers "generic" SQL, but most of it applies to SQLite as well)
A work-in-progress SQLite3 tutorial. Don't miss other LxyzTHW pages!
SQLite official website with full documentation (may be newer than the SQLite library that comes standard with AutoIt)

Share this post


Link to post
Share on other sites

#9 ·  Posted (edited)

After thinking about it, I see your point. I can imagine the scenario where a variable, a literal, or no argument at all can each have a separate interpretation or implementation. It was beyond my mortal comprehension a few moments ago. :baby:

Edited by czardas

Share this post


Link to post
Share on other sites

#10 ·  Posted (edited)

2 hours ago, czardas said:

Passing a literal ByRef, compiling the code and running it without throwing an error is odd behaviour from all parties involved. I still think that it's a bug and the compiler (and the OS) ought to reject it. Optional ByRef parameters are currently a feature request - not to confuse these two separate issues. One is probably a bug and the other is potentially a missing feature.

 

1 hour ago, jchd said:

I don't think so but I'd like @trancexx to jump in and tell us the Truth.

Here's how I see things working. When you invoke a function with a literal as argument, say MyFunc(42), the value 42 can't be just made off thin air: it has to be implemented in a (hidden) local variable, like genuine declared user variables. The same situation occurs when you write MyFunc(40 + 2) or  ConsoleWrite("A string" & @LF & "Another one." & @LF) where the result of the add/concat has to be stored in a hidden variable.

I find it quite natural that if MyFunc is declared accepting a ByRef argument, then a reference to that hidden variable be passed.

You might say that those hidden variables could be tagged Const, in which case any attempt to change them would raise an error, but since you can't access them anyway after the callee function terminates, the point is moot.

 

Quote

he value 42 can't be just made off thin air: it has to be implemented in a (hidden) local variable, like genuine declared user variables.

 

I cheked it now.. this code:

SomeFunc(42)

Func SomeFunc(ByRef $Output)
    $Output = 1
    ConsoleWrite($Output &' (L: '&@ScriptLineNumber&')'&@CRLF)
EndFunc

 

 

It prints "1"

which is tells me some important things:

  1. It indeed access+change data (what I wanted to know) otherwise it would not print 1. and the memory space of where the data stored is $Output and not 42 (otherwise it should crash..) .
    It mean that this is not acting like a pointer at all..

 

This example tell more information about what is happening beneath the surface:

Global $g_var = 0


SomeFunc($g_var)

Func SomeFunc(ByRef $Output)
    $Output = 1
    ConsoleWrite($Output &' (L: '&@ScriptLineNumber&')'&@CRLF) ; This will print 1
    ; Here the interpreter probably doing copy operation 
    ConsoleWrite($g_var &' (L: '&@ScriptLineNumber&')'&@CRLF) ; Print 1
    
EndFunc 


ConsoleWrite($g_var &' (L: '&@ScriptLineNumber&')'&@CRLF) ; Print 1

 

All this tell me something I would not guessed on my own - byref are not act like pointers in low level.
The interpreter still doing copy - So no performance/efficacy improvement  expected to occur (in memory)

And this is the important bottom line.

 

For me, it make no sence that interpreter will do this.. for me it is a bug or not efficient to implement the ByRef concept.
now that I know this bottom line, I have less reasons to use this ByRef concept

 

Edited by gil900

Share this post


Link to post
Share on other sites

#11 ·  Posted

You clearly don't understand the concept of reference.


This wonderful site allows debugging and testing regular expressions (many flavors available). An absolute must have in your bookmarks.
Another excellent RegExp tutorial. Don't forget downloading your copy of up-to-date pcretest.exe and pcregrep.exe here
RegExp tutorial: enough to get started
PCRE v8.33 regexp documentation latest available release and currently implemented in AutoIt beta.

SQLitespeed is another feature-rich premier SQLite manager (includes import/export). Well worth a try.
SQLite Expert (freeware Personal Edition or payware Pro version) is a very useful SQLite database manager.
An excellent eBook covering almost every aspect of SQLite3: a must-read for anyone doing serious work.
SQL tutorial (covers "generic" SQL, but most of it applies to SQLite as well)
A work-in-progress SQLite3 tutorial. Don't miss other LxyzTHW pages!
SQLite official website with full documentation (may be newer than the SQLite library that comes standard with AutoIt)

Share this post


Link to post
Share on other sites

#12 ·  Posted

Now I understand.. this means that instead of improving performance, it should do the opposite  because the interpreter copy data again and again every time I change the ByRef variable..

I confused it with pointer concept...

Share this post


Link to post
Share on other sites

#13 ·  Posted

There is no copy involved, you're still confused.


This wonderful site allows debugging and testing regular expressions (many flavors available). An absolute must have in your bookmarks.
Another excellent RegExp tutorial. Don't forget downloading your copy of up-to-date pcretest.exe and pcregrep.exe here
RegExp tutorial: enough to get started
PCRE v8.33 regexp documentation latest available release and currently implemented in AutoIt beta.

SQLitespeed is another feature-rich premier SQLite manager (includes import/export). Well worth a try.
SQLite Expert (freeware Personal Edition or payware Pro version) is a very useful SQLite database manager.
An excellent eBook covering almost every aspect of SQLite3: a must-read for anyone doing serious work.
SQL tutorial (covers "generic" SQL, but most of it applies to SQLite as well)
A work-in-progress SQLite3 tutorial. Don't miss other LxyzTHW pages!
SQLite official website with full documentation (may be newer than the SQLite library that comes standard with AutoIt)

Share this post


Link to post
Share on other sites

#14 ·  Posted

It must be an unintentional half-intended feature. ;)

Share this post


Link to post
Share on other sites

#15 ·  Posted (edited)

23 minutes ago, jchd said:

There is no copy involved, you're still confused.

 

This example
 

SomeFunc(Null)

Func SomeFunc(ByRef $Output)
    $Output = 1
    ConsoleWrite($Output &' (L: '&@ScriptLineNumber&')'&@CRLF) ; This will print 1
EndFunc

Telling me that it must to allocate new memory to store the value 1. otherwise a crash expected to happen.

Now that we have a basis to assume that this is what is actually happening  let's look at the next example:

Global $g_var
SomeFunc($g_var)
Func SomeFunc(ByRef $Output)
    $Output = 1 ; We assume here that it allocate new memory to store the value 1 (The previous example is the basis for this assumption)
    ConsoleWrite($g_var &' (L: '&@ScriptLineNumber&')'&@CRLF) ; This print 1 - what is the natural way to make it happen ? 
EndFunc

At line 5 it will print 1. The natural way to make it happen is to copy the value from the new memory space ($Output) to the memory space of $g_var

 

 

In the help file it says:

Quote

ByRef should be used when passing large amounts of data (such as the contents of a file) where copying all the data would impose a significant performance penalty.

This sentence tells me that a copy is not made.. but now I see that this is wrong info if my conclusion is correct .

Edited by gil900

Share this post


Link to post
Share on other sites

#16 ·  Posted

You conclusion is still incorrect. That's the whole purpose of passing parameters byref vs copying the content into a new local variable.


This wonderful site allows debugging and testing regular expressions (many flavors available). An absolute must have in your bookmarks.
Another excellent RegExp tutorial. Don't forget downloading your copy of up-to-date pcretest.exe and pcregrep.exe here
RegExp tutorial: enough to get started
PCRE v8.33 regexp documentation latest available release and currently implemented in AutoIt beta.

SQLitespeed is another feature-rich premier SQLite manager (includes import/export). Well worth a try.
SQLite Expert (freeware Personal Edition or payware Pro version) is a very useful SQLite database manager.
An excellent eBook covering almost every aspect of SQLite3: a must-read for anyone doing serious work.
SQL tutorial (covers "generic" SQL, but most of it applies to SQLite as well)
A work-in-progress SQLite3 tutorial. Don't miss other LxyzTHW pages!
SQLite official website with full documentation (may be newer than the SQLite library that comes standard with AutoIt)

Share this post


Link to post
Share on other sites

#17 ·  Posted

7 minutes ago, jchd said:

You conclusion is still incorrect. That's the whole purpose of passing parameters byref vs copying the content into a new local variable.

I do not understand why..  Please explain again

 

Share this post


Link to post
Share on other sites

#18 ·  Posted

Sorry I've very little time to expose how copy vs pointer vs reference work. Please turn on your browser and read up something there.


This wonderful site allows debugging and testing regular expressions (many flavors available). An absolute must have in your bookmarks.
Another excellent RegExp tutorial. Don't forget downloading your copy of up-to-date pcretest.exe and pcregrep.exe here
RegExp tutorial: enough to get started
PCRE v8.33 regexp documentation latest available release and currently implemented in AutoIt beta.

SQLitespeed is another feature-rich premier SQLite manager (includes import/export). Well worth a try.
SQLite Expert (freeware Personal Edition or payware Pro version) is a very useful SQLite database manager.
An excellent eBook covering almost every aspect of SQLite3: a must-read for anyone doing serious work.
SQL tutorial (covers "generic" SQL, but most of it applies to SQLite as well)
A work-in-progress SQLite3 tutorial. Don't miss other LxyzTHW pages!
SQLite official website with full documentation (may be newer than the SQLite library that comes standard with AutoIt)

Share this post


Link to post
Share on other sites

#19 ·  Posted (edited)

@gil900 When you pass a variable as argument to a function, a copy of that variable is created in the local scope. If the parameter is ByRef, then no copy is created.

Edited by czardas

Share this post


Link to post
Share on other sites

#20 ·  Posted

2 minutes ago, czardas said:

@gil900 When you pass a variable as argument to a function, a copy of that variable is created in the local scope. If the parameter is ByRef then no copy is made.

SomeFunc(Null)

Func SomeFunc(ByRef $Output)
    $Output = 1
    ConsoleWrite($Output &' (L: '&@ScriptLineNumber&')'&@CRLF) ; This will print 1
EndFunc

If no copy was made then it means that no new memory allocation for integer created -> then this was supposed to crash. it was not crash so it did allocation  which means that copy must be made if i wasn't pass to it null 

Or maybe I just lost my sanity 

Share this post


Link to post
Share on other sites

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