tags:

views:

947

answers:

4

Is there a way to set an object to the new instance of a class by using the text name of the class?

I will have a library of classes, and depending on some other variable, I want to get one of these classes at runtime.

E.g. I have "CTest1", "CTest2", "CTest3"

I would have function similar to the below

Function GetTestClass(lngClassNo as long) as Object

Dim strClassName as String
strClassName = "CTest" & CStr(lngClassNo)

Set GetTestClass = New instance of class(strClassName)

End Function

+2  A: 

There's no reflection in VBA, so I don't think this is possible. You'd have to do something like the following I'm afraid:

Function GetTestClass(lngClassNo as long) as Object

    Select Case lngClassNo
    Case 1
        Set GetTestClass = New CTest1
    Case 2
        Set GetTestClass = New CTest2
    ...

    End Select

End Function

Unless that is your CTest classes are defined in a COM DLL, in which case you could use the CreateObject statement. You would need to use VB6 to create such a DLL though, you can't create DLLs in Excel, Access, etc.

Function GetTestClass(lngClassNo as long) as Object

    Set GetTestClass = CreateObject("MyDll.CTest" & lngClassNo)

End Function
Patrick McDonald
I think you might run into casting issues if you tried to return an object. You would have to do something with a COM interface.
ConcernedOfTunbridgeWells
Oh well. I started of with a Select Case as above, but was hoping for something cleaner....not the end of the world. Thanks
MT
VBA allows late binding, so there are no casting issues as far as I can see, you just need to be careful to avoid runtime errors as the compiler won't pick up any typos in method names etc.
Patrick McDonald
These are the only two ways to pull off what you're suggesting. The interface suggestion from Concerned would simplify some of the implementation issues (I use interfaces frequently for this very purpose) so you can retain compile-time type checking in a polymorphic manner. However, you can still use runtime binding on the function calls with using an Object instance.
Joel Goodwin
Thanks for this. It's nice to be being able to use the interface. Just a shame about having to use the select case...
MT
+1  A: 

VB class definitions are really defining COM interfaces behind the scenes, so one can define data types as an abstract interface definition with concrete implementations using the implements keyword.

To get any sort of polymorphism you have to do this, otherwise you will have problems with casting. It is somewhat fiddly but technically possible to do this with VB. If you want to dig into it find some of the advanced VB books by Dan Appleman or Matthew Kurland. I'm not sure if they're still in print but they're probably available through Amazon Marketplace.

This works with VB6 and I'm fairly sure it works with VBA.

ConcernedOfTunbridgeWells
Very nice. It does work thanks. Nice to be able to use the compiler and not have to worry about typos etc.
MT
Implements just forces you implement all the public methods/properties of a given class. How would that help with creating a class by name?
Oorang
Creating an object is a no brainer. The problem is not creating the class but using it subequently. You can use Object and late binding and hope for the best. Implements gives you type-safe polymorphism.
ConcernedOfTunbridgeWells
A: 

You might be able to do it with a collection class or object array. All the objects are in one array.

In your class have a .Name property and when you create an instance of it do this:

Dim CTest() as New CTest
For n = 1 to 10
    Redim Preserve CTest(n)
    CTest(n).Name = "CTest" & CStr(n)
Next l

Quick and dirty. The above example would return 10 CTest objects in a single object array. You could also ditch the .Name and just use CTest(n).

mandroid
A: 

You've lost me a bit with this: how can polymorphism help you to create instances of a class using just a string?

I want to be able to look up in a table which class has to be used with a selected option. So how do you do this without using a select-statement?

Are you asking for the motiviation behind being able to do this?
MT
No more like how this is done
I don't think it can be in VBA as reflection is not supported. (Although I would love to be shot down on this and am not an expert in it).
MT