473,289 Members | 2,108 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes and contribute your articles to a community of 473,289 developers and data experts.

Determine if a Declared Array has been Initialised

NeoPa
32,554 Expert Mod 16PB
Introduction

NB. {Edit}
I subsequently found strange things happening in my project when I used this approach. Bizarre errors in code that had been working for years. When I removed this line of code it went back to working as before. I leave this here for information, but you have been warned.

Sometimes we need to determine if a declared array has been ReDimmed yet. If we try to reference it beforehand then it will crash. Not a good situation :-(

Here's an excerpt from the help file that may help to explain why this might occur :
ReDim Help:
The ReDim statement is used to size or resize a dynamic array that has already been formally declared using a Private, Public, or Dim statement with empty parentheses (without dimension subscripts).
I suspect they may have left out the Static statement, but that's another matter - not our issue here.

I will introduce and explain a way that allows the code to determine for itself, without triggering and capturing an error, whether or not the array variable has yet been initialised. For my purposes in this article I will refer to the act of ReDimming as initialisation. So, a dynamic array variable has no storage space allocated until it is initialised, or ReDimmed, but after its first ReDim it becomes initialised and does have storage space allocated.
ReDim Help:
Used at procedure level to reallocate storage space for dynamic array variables.
See the explanation below for how we'll take advantage of this to determine the initialised status of the dynamic array variable.


Explanation

A dynamic array variable has a pointer value of zero (0) until it is initialised, at which point the pointer value becomes non-zero. For our purposes we don't care about the value except as far as whether or not it's zero.

Generally, when an array variable is referenced without any qualifications, such as an element identifier specified for a dimension, the code will fail as directly referencing an array pointer is not allowed in VBA. That is to say, unless as a parameter to something like LBound() or UBound(). However, it is perfectly possible to reference it after the Not operator. We will use this to determine if it's been set yet or not.

If the pointer value is zero then Not of the pointer value is -1 - or all 1 bits. This isn't as easy to test as all zero bits (Zero.) so we use Not Not instead to return the original value of the pointer. We can compare this to zero, or we can even use CBool(), to determine if the dynamic array variable is unset yet.

NB.
What we cannot do is simply to test it as is. Not Not Not {dynamic array variable} is equivalent to Not {dynamic array variable}, but both of these will take the True path whether the original value of the pointer is zero or not. So, comparison with zero or the use of CBool() is indicated.


Code Illustration

Expand|Select|Wrap|Line Numbers
  1. Public Sub ReDimTest()
  2.     Dim astrVar() As String
  3.  
  4.     If (Not Not astrVar) = 0 Then Debug.Print "A Uninitialised"; (Not Not astrVar);
  5.     If Not Not astrVar Then Debug.Print " B Initialised"; (Not Not astrVar);
  6.     ReDim astrVar(0 To 1)
  7.     If (Not Not astrVar) = 0 Then Debug.Print " C Uninitialised"; (Not Not astrVar);
  8.     If Not Not astrVar Then Debug.Print " D Initialised"; (Not Not astrVar);
  9.     astrVar = Split("")
  10.     If (Not Not astrVar) = 0 Then Debug.Print " E Uninitialised"; (Not Not astrVar);
  11.     If Not Not astrVar Then Debug.Print " F Initialised"; (Not Not astrVar);
  12.     Debug.Print " G ";UBound(astrVar);
  13.     Debug.Print " H";astrVar(0);
  14. End Sub
Expand|Select|Wrap|Line Numbers
  1. Results:
  2. A Uninitialised 0 D Initialised 204031032 F Initialised 204031032 G -1 {Crashes here}
The error is Error #9 - Subscript out of range.

In the above code you'll notice that UBound(astrVar) returns a value of -1, which is below the lower bound of zero. Test this if you need to ensure that your code doesn't fall foul of any such situation.


Conclusion

I hope you find this useful :-)
Jan 15 '16 #1
1 7537
ADezii
8,834 Expert 8TB
Nice Article NeoPa! An interesting caveat here is that apparently the Array does not have to be formally declared with empty parenthesis as indicated by the Help File. The following Code works perfectly well with no prior Declaration:
Expand|Select|Wrap|Line Numbers
  1. ReDim aIntegers(1 To 5)
  2.  
  3. aIntegers(1) = 1111
  4. aIntegers(2) = 2222
  5. aIntegers(3) = 3333
  6. aIntegers(4) = 4444
  7. aIntegers(5) = 5555
  8.  
  9. Debug.Print aIntegers(1) & " | " & aIntegers(2) & " | " & aIntegers(3) & " | " & aIntegers(4) & " | " & aIntegers(5)
OUTPUT:
Expand|Select|Wrap|Line Numbers
  1. 1111 | 2222 | 3333 | 4444 | 5555
Apr 15 '16 #2

Sign in to post your reply or Sign up for a free account.

Similar topics

1
by: Ray | last post by:
Here's the code example... Dim myArray() as string later I will redim the array in a for/next or a Do/While Loop x = ubound(myArray) +1 <<< causes error 9 if no elements exist already!...
14
by: Roman Mashak | last post by:
Hello, All! Is there an easy way to determine that array e.g. int X contains ordered items (for example, ascending), except running loop with comparison of items? It would be good to provide...
0
by: Ray Stevens | last post by:
I have an IDL defined as follows: public StringBuilder LEGAL_FREEFORM ; In this case it is obvious that the Dim is 20 with a length of 78, however I want to be able to determine this at run...
3
by: AAOMTim | last post by:
Give the method ProcessArray as follows: void ProcessArray(Object objects) { foreach (Object object in objects) { // Do something } }
10
by: The Cool Giraffe | last post by:
I got a hint recently (guess where, hehe) and was directly pointed to the vector class. Now, i have no issues using that way but i'm concerned about the performance issue. Which is fastest...
4
by: Chronictank | last post by:
Hi, as a bit of background (and seeing as it is my first post :)) i am a complete newbie at perl. I literally picked it up a week ago to do this project as it seemed like the best choice for a...
2
by: JennyWren | last post by:
I have an array of structs which I will be going through one-by-one to search for a matching value. This array might have elements added and removed later, so I don't want to have to update a...
4
by: damiensawyer | last post by:
Hi, I've recently moved to c# framework 2 and have just discovered the comiler warning "The result of the expression is always 'false' since a value of type 'int' is never equal to 'null' of...
0
by: MeoLessi9 | last post by:
I have VirtualBox installed on Windows 11 and now I would like to install Kali on a virtual machine. However, on the official website, I see two options: "Installer images" and "Virtual machines"....
0
by: DolphinDB | last post by:
Tired of spending countless mintues downsampling your data? Look no further! In this article, you’ll learn how to efficiently downsample 6.48 billion high-frequency records to 61 million...
0
by: ryjfgjl | last post by:
ExcelToDatabase: batch import excel into database automatically...
0
isladogs
by: isladogs | last post by:
The next Access Europe meeting will be on Wednesday 6 Mar 2024 starting at 18:00 UK time (6PM UTC) and finishing at about 19:15 (7.15PM). In this month's session, we are pleased to welcome back...
0
by: marcoviolo | last post by:
Dear all, I would like to implement on my worksheet an vlookup dynamic , that consider a change of pivot excel via win32com, from an external excel (without open it) and save the new file into a...
1
isladogs
by: isladogs | last post by:
The next Access Europe meeting will be on Wednesday 6 Mar 2024 starting at 18:00 UK time (6PM UTC) and finishing at about 19:15 (7.15PM). In this month's session, we are pleased to welcome back...
0
by: Vimpel783 | last post by:
Hello! Guys, I found this code on the Internet, but I need to modify it a little. It works well, the problem is this: Data is sent from only one cell, in this case B5, but it is necessary that data...
0
by: ArrayDB | last post by:
The error message I've encountered is; ERROR:root:Error generating model response: exception: access violation writing 0x0000000000005140, which seems to be indicative of an access violation...
1
by: PapaRatzi | last post by:
Hello, I am teaching myself MS Access forms design and Visual Basic. I've created a table to capture a list of Top 30 singles and forms to capture new entries. The final step is a form (unbound)...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.