Results 1 to 9 of 9

Thread: Public Array of Integer Elements all Zeroed (without using code)

  1. #1

    Thread Starter
    Member
    Join Date
    Mar 2022
    Posts
    39

    Public Array of Integer Elements all Zeroed (without using code)

    I am using a QC method in Form1 (below) to determine whether Public variables develop problems throughout the application. Example problems (exceptions) would be integer values of zero, or arrays evaluating to Nothing, or Integer array elements of zero, or string array elements being equal to "". These public variables and arrays are used in different methods in Form1 as well as in different classes, via passing them to constructors of instantiated objects.

    Interestingly, there is a case when elements of the integer array InputRowID() array are all equal to zero, however, they were never programatically set to zero, e.g. using a loop. I can't seem to isolate where the array values are all zeroed when watching array elements everywhere. In addition, from what I can tell, none of the values of InputRowID() are zero when they are sent to this QC method

    I believe because all of the passed arguments are Public, and arrays are reference type, somehow the application is zeroing array elements when the Public variables are exposed to something. Therefore, what would cause all the elements of a Public integer array to bet set to zero without using code that zeroes all the elements?

    Also, are there rules of thumb about things you should never do with Public variables, such as never passing them at all, or passing them as ByVal or ByRef?

    Code:
    Public NumRows, NumCols As Integer
    Public InputRowID(100) As Integer
    Public InputRowNames(100), InputColNames(20), codelocation As String
    
    Public Sub QCOfPublicVars(ByVal NumRows As Integer, ByVal NumCols As Integer, ByVal ByVal InputRowID() As Integer, ByVal InputRowNames() As String, ByVal InputColNames() As String, ByVal codelocation as String)
         If NumRows = 0 Then
             MessageBox.Show("Error with NumRows at code location " & codelocation)
         End If
         If NumCols = 0 Then
             MessageBox.Show("Error with NumCols at code location " & codelocation)
         End If
         If InputRowID Is Nothing OrElse InputRowID(1) = 0 Then
             MessageBox.Show("Error with InputRowID at code location " & codelocation)
         End If
         If InputRowNames Is Nothing OrElse InputRowNames(1) Is Nothing OrElse InputRowNames(1) = "" Then
             MessageBox.Show("Error with InputRowNames at code location " & codelocation)
         End If
         If InputColNames Is Nothing OrElse InputColNames(1) Is Nothing OrElse InputColNames(1) = "" Then
             MessageBox.Show("Error with InputColNames at code location " & codelocation)
         End If
    End Sub

  2. #2
    Super Moderator Shaggy Hiker's Avatar
    Join Date
    Aug 2002
    Location
    Idaho
    Posts
    37,551

    Re: Public Array of Integer Elements all Zeroed (without using code)

    How are you passing the arrays? If you are passing them ByRef, that might be something to look at. After all, a new array of integers would be initialized to all 0. If you pass the array ByVal (the default), then it would take some positive action to clear the array. Not necessarily a loop, since you could do it with Array.Copy, as well, but it would still take positive action. If you are passing the array ByRef, then some method might be swapping the array you pass in for a new array, which would be all zeroes.
    My usual boring signature: Nothing

  3. #3

    Thread Starter
    Member
    Join Date
    Mar 2022
    Posts
    39

    Re: Public Array of Integer Elements all Zeroed (without using code)

    Thanks @Shaggy Hiker. The only time I use ByRef is when I load the params/arrays during deserialization from a JSON file like the method below. However, I learned that the name of the param/array has to be changed in order to load the data into the Public params/arrays. Is this not true? Should I drop the "s" before each argument?

    (Please not that when serializing the param/array values, I use ByVal in that Class, which has properties names that are identical to the params/arrays)

    The deserialization call to the JSON file is, along with the QC check:
    Code:
    Dim deser As New deserializeinputparams(NumRows, NumCols, InputRowID, InputRowNames, InputColNames, filename)
    QCOfPublicVars(NumRows, NumCols, InputRowID, InputRowNames, InputColNames, "Method XYZ, deser")
    The code for the deserialization class is:

    Code:
    <Serializable()>
    Public Class deserializeinputparams
        Public jsonpath As String
        Sub New()
    
        End Sub
        Sub New(ByRef sNumRows As Integer, ByRef sNumCols As Integer, ByRef sInputRowID() As Integer, ByRef sInputRowNames() As String, ByRef sInputColNames() As String, ByRef sfilename As String)
            Call deserinputparams(sNumRows, sNumCols, sInputRowID, sInputRowNames, sInputColNames, sfilename)
        End Sub
        Sub deserinputparams(ByRef sNumRows As Integer, ByRef sNumCols As Integer, ByRef sInputRowID() As Integer, ByRef sInputRowNames() As String, ByRef sInputColNames() As String, ByRef sfilename As String)
            If File.Exists(jsonpath) Then
                Try
                    Using reader As New StreamReader(jsonpath, Encoding.UTF8)
                        Dim jReader As New JsonTextReader(reader) With {.FloatParseHandling = FloatParseHandling.Double}
                        Dim serializer As New JsonSerializer()
                        Dim deserialized = serializer.Deserialize(Of serializeinputparams)(jReader)
                        jReader.Close()
                        If deserialized Is Nothing Then Exit Sub
                        sNumRows = deserialized.NumRows
                        sNumCols = deserialized.NumCols
                        sInputRowID = deserialized.InputRowID
                        sInputRowNames = deserialized.InputRowNames
                        sInputColNames = deserialized.InputColNames
                        sfilename = deserialized.Filename
                        deserialized = Nothing
                    End Using
            Else
                Exit Sub
            End If
        End Sub
    End Class
    Last edited by pel11; Apr 9th, 2022 at 07:06 PM.

  4. #4
    Super Moderator Shaggy Hiker's Avatar
    Join Date
    Aug 2002
    Location
    Idaho
    Posts
    37,551

    Re: Public Array of Integer Elements all Zeroed (without using code)

    You can pretty easily determine whether or not that code is causing the problem, and on it's own, it doesn't look likely. However, it does result in a new array. As long as the JSON contains an array that does what you want, then the code shown isn't the problem.

    Having said that, there are a couple further points to be made about that. For one thing, that code DOES result in a new array. Therefore, you might check what the array looks like at the end of that method. Validate it there. If it's bad at that point, then it certainly will be bad elsewhere. Of course, that would mean that your JSON file doesn't hold what you think it holds, but when looking for an issue, it's always good to verify your assumptions.

    A second point is that your class doesn't make a lot of sense, as shown. The one constructor does nothing, the other constructor isn't a constructor at all. The same result could be obtained by putting the deserinputparams() function in a module, or if that class contains other stuff that you didn't show, then make that method Shared and get rid of that second constructor. After all, the method isn't setting any class level variables...nor do you show any, so it stands alone.
    My usual boring signature: Nothing

  5. #5
    PowerPoster
    Join Date
    Nov 2017
    Posts
    2,079

    Re: Public Array of Integer Elements all Zeroed (without using code)

    In your case, based on your code snippet, I can't think of a good reason why you would want to pass any public variables as parameters, since you are using all of the public variables as-is. Since the parameter names match the public variable names, you wouldn't even need to change anything inside of that sub, just change the sub parameter list to remove all but the last parameter (codelocation).

  6. #6

    Thread Starter
    Member
    Join Date
    Mar 2022
    Posts
    39

    Re: Public Array of Integer Elements all Zeroed (without using code)

    Thanks for the detailed information. I'll try making the class a function in a module, as it would probable save on instantiating the object (class) every time it's used. Will watch at the end of the class to see if anything is zeroed, same as the serializing class. The class wouldn't work for some reason without the empty constructor, and there were some hits on that issue for JSON at StackExchange I recall.

  7. #7

    Thread Starter
    Member
    Join Date
    Mar 2022
    Posts
    39

    Re: Public Array of Integer Elements all Zeroed (without using code)

    I found part of the culprit. If you have a public array x() as integer for example, and then call a method as in

    Code:
    Public X(100) As Integer
    
    For i = 0 to 99
       X(i) = 5
    Next i
    Math(X)
    and the math method is

    Code:
    Sub Math(ByRef Y() As Integer)
    
      Redim Y(100)
    
    Endif
    as soon as you redim Y you will wipe out or zero everything in X. This is what was happening in some code.

  8. #8
    Smooth Moperator techgnome's Avatar
    Join Date
    May 2002
    Posts
    33,908

    Re: Public Array of Integer Elements all Zeroed (without using code)

    If you want to change the size of the array whilst keeping the existing values in it, use ReDim Preserve.

    -tg
    * I don't respond to private (PM) requests for help. It's not conducive to the general learning of others.*
    * I also don't respond to friend requests. Save a few bits and don't bother. I'll just end up rejecting anyways.*
    * How to get EFFECTIVE help: The Hitchhiker's Guide to Getting Help at VBF - Removing eels from your hovercraft *
    * How to Use Parameters * Create Disconnected ADO Recordset Clones * Set your VB6 ActiveX Compatibility * Get rid of those pesky VB Line Numbers * I swear I saved my data, where'd it run off to??? *

  9. #9
    Super Moderator Shaggy Hiker's Avatar
    Join Date
    Aug 2002
    Location
    Idaho
    Posts
    37,551

    Re: Public Array of Integer Elements all Zeroed (without using code)

    That's what I said in my first post. Passing arrays ByRef is a likely source of the problem. Unless you have a good reason to pass arrays ByRef, then you should pass them ByVal. The only good reason to pass an array ByRef would be if you intend to replace the array with a new array.

    One thing to note is that ReDim and ReDim Preserve both get rid of the original array. You can't change the size of an array, so when you call either of those, you create a new array of the new size. With Preserve, there is an additional step where you then move items from the old to the new, but with ReDim you are just creating a new array. If you are doing a lot of that, you should consider using a List(of Integer) rather than an array.
    My usual boring signature: Nothing

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Click Here to Expand Forum to Full Width