tags:

views:

1231

answers:

5

Its been a while since I've worked with ASP, but I'm getting a Type mismatch error on what seems to be a simple assignment statement. Can anyone shed some light on why this might be happening.

This works, but when I try to foreach an unassigned Questions block I get an Object not a collection error

Class Survey
  public ID
  public Title
  public Questions
End Class

Sub Test()
  Dim oSurvey
  Set oSurvey = new Survey
  Dim aQuestions(2)
  Set aQuestions(0) = new Question
  ' Other aQuestions assignments
  oSurvey.Questions = aQuestions
End Sub

Alternately If I setup questions as a dynamic array then the assignment fails with a type mismatch error.

Class Survey
  public ID
  public Title
  public Questions()
End Class

Sub Test()
  Dim oSurvey
  Set oSurvey = new Survey
  Dim aQuestions(2)
  Set aQuestions(0) = new Question
  ' Other aQuestions assignments
  ' Throws a Type mismatch error here
  oSurvey.Questions = aQuestions
End Sub

Any thoughts?

A: 

If I try to paste the same code into VBA (excel or word), it doesn't compile.

It shows error on line public Questions() saying

---------------------------
Microsoft Visual Basic
---------------------------
Compile error:

Constants, fixed-length strings, arrays, user-defined types and Declare statements not allowed as Public members of object modules
---------------------------
OK   Help   
---------------------------

In the first example, you haven't defined it as an array (it is a variant & hence can be assigned any value).

shahkalpesh
if you want to try testing this in VBA i think you'd have to create a class module instead of the class/end class
bendewey
Sure. The idea was to understand why it fails.
shahkalpesh
A: 

Update: I tested this in ASP.NET not realizing the question was about classic ASP. I've modified the code below to work with classic ASP, though I haven't been able to test it yet:

    Class Question
        ...
    End Class

    Class Survey
        Public ID
        Public Title
        Public Questions As Question()
    End Class

    Sub Test()
        Dim oSurvey As New Survey
        Dim aQuestions(0 To 2) As Question
        Set aQuestions(0) = New Question
        ...
        Set oSurvey.Questions = aQuestions
    End Sub

In your first example, Survey.Questions isn't a collection; in your second, it is an array of Type Variant.

elo80ka
The error I'm receiving is in classic asp
bendewey
I'm thinking the above code should still work, although you'll probably have to use the `Set` keyword before each object assignment. I'll update the answer.
elo80ka
I'm getting an error using the AS keyword in classic asp
bendewey
Silly me - forgot that ASP uses Variants. Glad you found a solution though.
elo80ka
A: 

Have you tried using Scripting.Dictionary instead of an array?

DaveJustDave
A: 

So I ended up sticking with the Array declaration. Additionally, When I tried to ReDim the array like so I got an error.

ReDim oSurvey.Questions(2)

So I created a sub routine to ReDim the Array, and this worked.

Class Survey
  public ID
  public Title
  public Questions()

  sub ReDimQuestions(count)
    ReDim Questions(count)
  end sub
End Class

Sub Test()
  Dim oSurvey
  Set oSurvey = new Survey
  oSurvey.ReDimQuestions 2
  Set oSurvey.Questions(0) = new Question
  ' Other aQuestions assignments
End Sub
bendewey
+1  A: 

To answer your question as to what is actually going on.

when I try to foreach an unassigned Questions block I get an Object not a collection error

For Each enumerates a set of variants from the source variable, it does this by acquiring an IEnumVARIANT. If the source variable holds an object it is expected to have an implementation of this interface. If it is an array VBScript creates an implementation dynamically and it can only do this if the array has been dimensioned. Anything else in the source variable (such as Empty in this case) will result in an error.

then the assignment fails with a type mismatch error.

The left hand side of an assignment operation must always be a variant. Hence its not possible copy the contents of one dynamic array to another via a simple assignment.

Your first approach is reasonably sound but you need a way to represent an empty array without crashing out a For Each. You can use this little trick:-

Function EmptyArray
EmptyArray = Split("", " ")
End Function

Class Survey
   public ID
   public Title
   public Questions

   Private Sub Class_Initialize
       Questions = EmptyArray
   End Sub
End Class

Now if you try to For Each the Questions before it has been assigned a real array the for each will do nothing as expected. Also if you use UBound(Questions) + 1 to get the count of questions that will still be accurate since UBound(EmptyArray) is -1.

AnthonyWJones
Thanks, this makes sense now.
bendewey