Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Incorrect array indexing when passed as parameter #824

Open
oskostenko opened this issue Oct 8, 2024 · 6 comments · May be fixed by #852
Open

Incorrect array indexing when passed as parameter #824

oskostenko opened this issue Oct 8, 2024 · 6 comments · May be fixed by #852
Assignees
Labels

Comments

@oskostenko
Copy link

Hi,

Having the following code:

sub PrintArray(arr() as integer)
    dim i as integer
    for i = lbound(arr, 1) to ubound(arr, 1)
        print i; ": "; arr(i)
    next i
end sub

dim arr(1 to 3) as integer => {10, 20, 30}

PrintArray arr

The expected output is:

1: 10
2: 20
3: 30

Actual output:

1: 20
2: 30
3: 0

Is it a bug or a feature?

@boriel boriel added the bug label Oct 11, 2024
@boriel
Copy link
Collaborator

boriel commented Oct 11, 2024

Thanks for reporting.
Indeed this is a long known bug: functions are unaware of array dimensions. They will always access the array with the array-base. The solution is not easy (or at least a performant / efficient one).
I was thinking on removing the feature of allowing declaring arrays with lower and upper dimensions, and use only number of elements (like in C and other languages), because is a nightmare and a feature seldom used.

Using #pragma array_base=1 or the --array-base=1 command line flag has the same effect and prevents this problem.

Will keep you updated with the fix of this. :-)

@oskostenko
Copy link
Author

Thank you very much for replying.

functions are unaware of array dimensions

What's the most annoying here, is that lbound and ubound inside the function are aware of array dimensions, and work inconsistently with how the array is actually accessed.

Using #pragma array_base=1 or the --array-base=1 command line flag has the same effect and prevents this problem.

Alas, it doesn't prevent the problem:

#pragma array_base=1

sub PrintArray(arr() as integer)
    dim i as integer
    for i = lbound(arr, 1) to ubound(arr, 1)
        print i; ": "; arr(i)
    next i
end sub

dim arr(3) as integer => {10, 20, 30}

PrintArray arr

Gives the same incorrect output:

1: 20
2: 30
3: 0

I hope this will be fixed soon. To me, 1-based arrays seem very beneficial in Basic, because I find it very awkward to always calculate length - 1 when declaring arrays and iterating over them. Zero-based arrays are absolutely fine in languages like C because of the way they are declared and iterated over, but not in Basic..

@boriel
Copy link
Collaborator

boriel commented Oct 13, 2024

Yes, but that's because, regardless of the array base functions are totally agnostic of the arrays and dimensions they receive, and operate on base 0. Giving support to these will be very expensive (in terms on memory and speed), but can be done using using the internal LBound and UBound tables. I will try to implement a solution.

In the (long) meantime, you can use lbound to subtract the index if needed. In your case:

#pragma array_base=1

sub PrintArray(arr() as integer)
    dim i as integer
    for i = 0 to ubound(arr, 1) - lbound(arr, 1)
        print i; ": "; arr(i)
    next i
end sub

dim arr(3) as integer => {10, 20, 30}

PrintArray arr

This will work regardless of how the array was declared and the array base.
If you want to retrieve the original index, use Lbound(arr, 1) + i

EDIT: Array declarations will be changed in the future 2.x, and all of them will be 0-based or 1-based only. I'm seriously considering removing the DIM a(x1 TO y1, x2 TO y2...) syntax.
This will allow a simpler implementation in array access within functions that will operate on the array_base selected (array base can be dynamically changed using #pragma as the example above, so a function can temporarily enforce array_base 0 and restore the previous one upon return, making it compatible to any type of array -i.e. when implementing a library).

@boriel
Copy link
Collaborator

boriel commented Oct 28, 2024

Please, consider joining the official telegram channel to discuss this with the community:
https://t.me/+ydBiLEzi0_M1OWZk

@boriel boriel linked a pull request Nov 3, 2024 that will close this issue
@boriel boriel self-assigned this Nov 3, 2024
@oskostenko
Copy link
Author

Works correctly now, thank you! 👍

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
Status: In Progress
Development

Successfully merging a pull request may close this issue.

2 participants