By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
443,572 Members | 1,516 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 443,572 IT Pros & Developers. It's quick & easy.

Shared constructor not called before Shared method

P: n/a
I have a base class with several derived classes (I'm writing in
VB.NET). I want each derived class to have a unique class ID (a
String), and I want the derived classes to inherit from the base
class *Shared* methods which make use of the class ID.

So I gave the base class a classID field, and then I gave the
derived classes Shared constructors, which I used to set the classID
field to the appropriate values for each derived class. But this
doesn't work! In the example below the method

DerivedClass.PrintClassID()

prints the class ID for the base class, rather than the derived
class. So the Shared constructor for the derived class, which is
needed to properly initialize the inherited Shared methods of that
class, is not getting called.

However if I create an instance (xyz in the example) of the derived
class the Shared constructor *does* get called, even if I do nothing
with the class instance. This just seems wrong. One would expect
that the Shared fields of a class should get initialized before
any class Shared methods get called, and that this initialization
should not depend on the creation of an actual instance of the class.

So what is going on? Is this an outstanding bug, or a misfeature
that people have resigned themselves to living with, or have I
simply misunderstood a feature? And what should I do to get the
result I want? I can Shadow the PrintClassID method, and then it
works as expected. But I don't want to have to Shadow every method
which uses the classID field -- the whole point was that all that
functionality was to be handled entirely by the base class, without
the derived classes needing to know anything abou it.

Any thoughts?

'===== Begin Example =====
Imports System

Class BaseClass
Protected Shared classID As String = "BaseClass!"

Public Shared Sub PrintClassID()
Console.WriteLine("classID = " & classID)
End Sub
End Class

Class DerivedClass
Inherits BaseClass

Shared Sub New()
classID = "DerivedClass!"
End Sub
End Class
Module TestModule
Public Sub Main()

'Dim xyz As New DerivedClass
DerivedClass.PrintClassID()

End Sub
End Module
'===== End Example =====
--
John Brock
jb****@panix.com

Nov 21 '05 #1
Share this Question
Share on Google+
10 Replies


P: n/a
John,
DerivedClass.PrintClassID()
This simply compiles to a call to BaseClass.PrintClassID, and
DerivedClass never has to be loaded.

And what should I do to get the result I want?


If you want polymorphism you should be using instance members instead
of Shared.
Mattias

--
Mattias Sjögren [MVP] mattias @ mvps.org
http://www.msjogren.net/dotnet/ | http://www.dotnetinterop.com
Please reply only to the newsgroup.
Nov 21 '05 #2

P: n/a
In article <Ox**************@TK2MSFTNGP09.phx.gbl>,
Mattias Sjögren <ma********************@mvps.org> wrote:
John,
DerivedClass.PrintClassID() This simply compiles to a call to BaseClass.PrintClassID, and
DerivedClass never has to be loaded.
But I explicitly asked for it to be loaded! Since these are shared
methods there is no concern about typing, and there is nothing
stopping me from calling BaseClass.PrintClassID at any time, if
that were what I wanted.

On page 181 of Paul Vick's excellent VB.NET book he notes that "the
general rule of thumb is that a the shared constructor will be run
before anything that could depend on it can be accessed". This
led me to believe that .NET would do what seems to me the natural
thing, which is that if a class had a shared constructor, it would
be run to initialize the class before any of the classes' shared
methods were run.
And what should I do to get the result I want?

If you want polymorphism you should be using instance members instead
of Shared.


Well sure, you can *always* use instance members instead of Shared.
So what then is the point of the .NET framework having Shared
members at all? It's because some information really belongs to
the class rather than the instances, and it is convenient to be
able to access that information without having to go to the trouble
of creating an instance. In this case I am going to have to create
actual instances of my derived classes which I am only going to use
to get meta-information about the classes themselves. This is
not hard, but seems kind of silly.

I guess if you can't do it then you can't do it. But I am still
curious whether this is an oversight -- a defect in the language
-- or whether there is perhaps some good reason why what I want to
do would cause problems and *shouldn't* be allowed. Do you have
any idea what the reasoning is, or do you know any web pages where
this is discussed?
--
John Brock
jb****@panix.com

Nov 21 '05 #3

P: n/a

"John Brock" <> wrote in message news:dg**********@reader1.panix.com...
:
: I have a base class with several derived classes (I'm writing in
: VB.NET). I want each derived class to have a unique class ID (a
: String), and I want the derived classes to inherit from the base
: class *Shared* methods which make use of the class ID.
:
: So I gave the base class a classID field, and then I gave the
: derived classes Shared constructors, which I used to set the classID
: field to the appropriate values for each derived class. But this
: doesn't work! In the example below the method
:
: DerivedClass.PrintClassID()
:
: prints the class ID for the base class, rather than the derived
: class. So the Shared constructor for the derived class, which is
: needed to properly initialize the inherited Shared methods of that
: class, is not getting called.
:
: However if I create an instance (xyz in the example) of the derived
: class the Shared constructor *does* get called, even if I do nothing
: with the class instance. This just seems wrong. One would expect
: that the Shared fields of a class should get initialized before
: any class Shared methods get called, and that this initialization
: should not depend on the creation of an actual instance of the class.
:
: So what is going on? Is this an outstanding bug, or a misfeature
: that people have resigned themselves to living with, or have I
: simply misunderstood a feature? And what should I do to get the
: result I want? I can Shadow the PrintClassID method, and then it
: works as expected. But I don't want to have to Shadow every method
: which uses the classID field -- the whole point was that all that
: functionality was to be handled entirely by the base class, without
: the derived classes needing to know anything abou it.
:
: Any thoughts?
:
: '===== Begin Example =====
: Imports System
:
: Class BaseClass
: Protected Shared classID As String = "BaseClass!"
:
: Public Shared Sub PrintClassID()
: Console.WriteLine("classID = " & classID)
: End Sub
: End Class
:
: Class DerivedClass
: Inherits BaseClass
:
: Shared Sub New()
: classID = "DerivedClass!"
: End Sub
: End Class
:
:
: Module TestModule
: Public Sub Main()
:
: 'Dim xyz As New DerivedClass
: DerivedClass.PrintClassID()
:
: End Sub
: End Module
: '===== End Example =====
: --
: John Brock
Note, I believe you should refrain from using your actual email address
in these posts as they can be scanned by bots that seek them out in
order to include in spam lists. I could be mistaken, but I don't think
so. Mask your email address instead (e.g.: jB****@REMOVEpanix.com or
something along those lines). This should be the case both for your sig
blocks as well as the email address you use in your newreader.
In any event, how about the following?
---------------------------------------
Option Strict

Imports Microsoft.VisualBasic
Imports System

Public Class Base
Public Overridable ReadOnly Property ClassID As String
Get
Return "Base"
End Get
End Property

Public Overridable Sub PrintClassID()
SharedFunction(ClassID)
End Sub

Protected Shared Sub SharedFunction(ClassID As String)
Console.WriteLIne(ClassID)
End Sub
End Class

Public Class Derived1 : Inherits Base
Public Overrides ReadOnly Property ClassID As String
Get
Return "Derived1"
End Get
End Property

Public Overrides Sub PrintClassID()
SharedFunction(ClassID)
End Sub
End Class

Public Class Derived2 : Inherits Base
Public Overrides ReadOnly Property ClassID As String
Get
Return "Derived2"
End Get
End Property

Public Overrides Sub PrintClassID()
SharedFunction(ClassID)
End Sub
End Class

Public Module [module]
Public Sub Main
Dim b As New Base
Dim d1 As New Derived1
Dim d2 As New Derived2

b.PrintClassID
d1.PrintClassID
d2.PrintClassID
End Sub
End Module
---------------------------------------
This will generate the following output:
Base
Derived1
Derived2
HTH
Ralf
--
----------------------------------------------------------
* ^~^ ^~^ *
* _ {~ ~} {~ ~} _ *
* /_``>*< >*<''_\ *
* (\--_)++) (++(_--/) *
----------------------------------------------------------
There are no advanced students in Aikido - there are only
competent beginners. There are no advanced techniques -
only the correct application of basic principles.
Nov 21 '05 #4

P: n/a

"_AnonCoward" <ab*@xyz.com> wrote in message
news:aG********************@twister.southeast.rr.c om...
:
: "John Brock" <> wrote in message
: news:dg**********@reader1.panix.com...
: :
: : I have a base class with several derived classes (I'm writing in
: : VB.NET). I want each derived class to have a unique class ID (a
: : String), and I want the derived classes to inherit from the base
: : class *Shared* methods which make use of the class ID.
: :
: : So I gave the base class a classID field, and then I gave the
: : derived classes Shared constructors, which I used to set the classID
: : field to the appropriate values for each derived class. But this
: : doesn't work! In the example below the method
: :
: : DerivedClass.PrintClassID()
: :
: : prints the class ID for the base class, rather than the derived
: : class. So the Shared constructor for the derived class, which is
: : needed to properly initialize the inherited Shared methods of that
: : class, is not getting called.
: :
: : However if I create an instance (xyz in the example) of the derived
: : class the Shared constructor *does* get called, even if I do nothing
: : with the class instance. This just seems wrong. One would expect
: : that the Shared fields of a class should get initialized before
: : any class Shared methods get called, and that this initialization
: : should not depend on the creation of an actual instance of the
: : class.
: :
: : So what is going on? Is this an outstanding bug, or a misfeature
: : that people have resigned themselves to living with, or have I
: : simply misunderstood a feature? And what should I do to get the
: : result I want? I can Shadow the PrintClassID method, and then it
: : works as expected. But I don't want to have to Shadow every method
: : which uses the classID field -- the whole point was that all that
: : functionality was to be handled entirely by the base class, without
: : the derived classes needing to know anything abou it.
: :
: : Any thoughts?
: :
: : '===== Begin Example =====
: : Imports System
: :
: : Class BaseClass
: : Protected Shared classID As String = "BaseClass!"
: :
: : Public Shared Sub PrintClassID()
: : Console.WriteLine("classID = " & classID)
: : End Sub
: : End Class
: :
: : Class DerivedClass
: : Inherits BaseClass
: :
: : Shared Sub New()
: : classID = "DerivedClass!"
: : End Sub
: : End Class
: :
: :
: : Module TestModule
: : Public Sub Main()
: :
: : 'Dim xyz As New DerivedClass
: : DerivedClass.PrintClassID()
: :
: : End Sub
: : End Module
: : '===== End Example =====
: : --
: : John Brock
I just realized there is even a cleaner approach. This will produce the
same result as my previous code:
---------------------------------------
Option Strict

Imports Microsoft.VisualBasic
Imports System

Public Class Base
Public Overridable ReadOnly Property ClassID As String
Get
Return "Base"
End Get
End Property

Public Overridable Sub PrintClassID()
Console.WriteLIne(ClassID)
End Sub

End Class

Public Class Derived1 : Inherits Base
Public Overrides ReadOnly Property ClassID As String
Get
Return "Derived1"
End Get
End Property

End Class

Public Class Derived2 : Inherits Base
Public Overrides ReadOnly Property ClassID As String
Get
Return "Derived2"
End Get
End Property

End Class

Public Module [module]
Public Sub Main
Dim b As New Base
Dim d1 As New Derived1
Dim d2 As New Derived2

b.PrintClassID
d1.PrintClassID
d2.PrintClassID
End Sub
End Module
---------------------------------------
Ralf
--
----------------------------------------------------------
* ^~^ ^~^ *
* _ {~ ~} {~ ~} _ *
* /_``>*< >*<''_\ *
* (\--_)++) (++(_--/) *
----------------------------------------------------------
There are no advanced students in Aikido - there are only
competent beginners. There are no advanced techniques -
only the correct application of basic principles.

Nov 21 '05 #5

P: n/a
In article <yq********************@twister.southeast.rr.com >,
_AnonCoward <ab*@xyz.com> wrote:
[...]
I just realized there is even a cleaner approach. This will produce the
same result as my previous code:
---------------------------------------
Option Strict

Imports Microsoft.VisualBasic
Imports System

Public Class Base
Public Overridable ReadOnly Property ClassID As String
Get
Return "Base"
End Get
End Property

Public Overridable Sub PrintClassID()
Console.WriteLIne(ClassID)
End Sub

End Class

Public Class Derived1 : Inherits Base
Public Overrides ReadOnly Property ClassID As String
Get
Return "Derived1"
End Get
End Property

End Class

Public Class Derived2 : Inherits Base
Public Overrides ReadOnly Property ClassID As String
Get
Return "Derived2"
End Get
End Property

End Class

Public Module [module]
Public Sub Main
Dim b As New Base
Dim d1 As New Derived1
Dim d2 As New Derived2

b.PrintClassID
d1.PrintClassID
d2.PrintClassID
End Sub
End Module
---------------------------------------


Actually you missed the point of my question. I was interested in
*Shared* methods, and getting the class to initialize itself via
the Shared constructor without actually having to create any
instances of the class. .NET seems determined to disallow this.
I had already tried using Shared properties, but .NET won't allow
Overrides and Overridable with Shared properties, and using Shadows
on the property in the derived class doesn't fix the problem (i.e.,
the Shared constructor still isn't called).

However I did find a workaround. If I give the derived class an
empty Shared DoNothing method that the base class doesn't have and
then call DerivedClass.DoNothing this *does* cause the Shared
constructor of DerivedClass to execute, without the expense of
creating a class instance where one isn't needed. It still means
that I have to explicitly initialize the class though, which is
annoying.

More and more this is looking like an easily fixable language design
flaw to me. Can anyone think of a reason why a Shared constructor
*shouldn't* execute if a Shared method is called before a class
has been instantiated? I realize the odds aren't good of anything
coming of it, but is there a place to go to formally bring this
issue to Microsoft's attention?
--
John Brock
jb****@panix.com

Nov 21 '05 #6

P: n/a

"John Brock" <jb****@panix.com> wrote in message
news:dg**********@reader1.panix.com...
In article <yq********************@twister.southeast.rr.com >,
_AnonCoward <ab*@xyz.com> wrote:
[Snipped]

Actually you missed the point of my question. I was interested in
*Shared* methods, and getting the class to initialize itself via
the Shared constructor without actually having to create any
instances of the class. .NET seems determined to disallow this.
I had already tried using Shared properties, but .NET won't allow
Overrides and Overridable with Shared properties, and using Shadows
on the property in the derived class doesn't fix the problem (i.e.,
the Shared constructor still isn't called).

However I did find a workaround. If I give the derived class an
empty Shared DoNothing method that the base class doesn't have and
then call DerivedClass.DoNothing this *does* cause the Shared
constructor of DerivedClass to execute, without the expense of
creating a class instance where one isn't needed. It still means
that I have to explicitly initialize the class though, which is
annoying.

More and more this is looking like an easily fixable language design
flaw to me. Can anyone think of a reason why a Shared constructor
*shouldn't* execute if a Shared method is called before a class
has been instantiated? I realize the odds aren't good of anything
coming of it, but is there a place to go to formally bring this
issue to Microsoft's attention?
--
John Brock
jb****@panix.com


John,

Your proposed method will not work either; I'll explain further down.
I think the problem is that you are already blinded by frustration.
So lets take a step back and start over.

First, you must Shadow the desired method in your derived class.
This is due to the fact that you want different behaviour and/or results.
The reason your constructor in the Derived class is never executed is
because the Derived class is never used. If you do not Shadow the method of
the Base class, then the compiler has no way of knowing that it is to
execute the method on your Derived class instead of the Base class, so the
Base class is used.

In it's simplest form, you would need something like:
'----------------------------------------
Public Class BaseClass
Public Shared Function ClassID() As String
Return "BaseClass"
End Function
End Class

Public Class DerivedClass : Inherits BaseClass
Public Shared Shadows Function ClassID() As String
Return "DerivedClass"
End Function
End Class
'----------------------------------------

There is really no way around it. Since you expect a different return value,
you must provide an implementation in your Derived class.

Now the reason your latest suggested method will still not work is more of a
scoping issue. If the constructor on your Derived class were to actually
run, then you would actually be changing the ClassID variable in your Base
class. This would be bad.
For a working example of what NOT to do, try the following:
'----------------------------------------
Public Class BaseClass
Protected Shared m_ClassID As String = "BaseClass"

Public Shared Function ClassID() As String
Return m_ClassID
End Function
End Class

Public Class DerivedClass : Inherits BaseClass
Public Shared Shadows Function ClassID() As String
Return m_ClassID
End Function

Shared Sub New()
m_ClassID = "DerivedClass"
End Sub
End Class
'----------------------------------------

Now look at the results:
'Produces "BaseClass"
Console.WriteLine(BaseClass.ClassID)
'Produces "DerivedClass"
Console.WriteLine(DerivedClass.ClassID)
'ALSO Produces "DerivedClass"
Console.WriteLine(BaseClass.ClassID)

Since the ClassID is only declared in the Base class and is Shared amongst
all derivatives, altering it in any of the classes in the family will alter
the Base class itself.

If you truly desired to use Shared class type variables, then they must be
isolated to each class type. The following is a working example of using a
Shared class type variable along with a Shared constructor:
'----------------------------------------
Public Class BaseClass
Private Shared m_ClassID As String

Public Shared Function ClassID() As String
Return m_ClassID
End Function

Shared Sub New()
m_ClassID = "BaseClass"
End Sub
End Class

Public Class DerivedClass : Inherits BaseClass
Private Shared m_ClassID As String

Public Shared Shadows Function ClassID() As String
Return m_ClassID
End Function

Shared Sub New()
m_ClassID = "DerivedClass"
End Sub
End Class
'----------------------------------------

If you try this, you will see that both constructors are called as expected,
and you also get the expected results. The Private declaration provides,
even enforces, the desired level of isolation. But the common theme here is
that you must Shadow the ClassID function in all your Derived classes,
otherwise the method on the Base class will be executed.
Since Shadowing of the method is required regardless, I am partial to the
very first example since it provides the least amount of typing.

Does this help to clear things up a little bit?

Gerald
Nov 21 '05 #7

P: n/a
On 2005-09-21, John Brock <jb****@panix.com> wrote:

More and more this is looking like an easily fixable language design
flaw to me. Can anyone think of a reason why a Shared constructor
*shouldn't* execute if a Shared method is called before a class
has been instantiated?
This is actually a pretty good question, but the answer might be
complex. And I haven't really thought out all the permutations
involved. The problem with discussing vague language ideas like the
above is that as you try to define the behavior, each decision you make
creates a new complex topic to think through.

First, you really need to understand that what you're trying to do
is generally a considered a bad idea. It's not that anyone "puts
up with this limitation", it's that this situation doesn't usually
come up, because it's just not a good idea.

Next, the implementation is problematic. What you're really asking for
here is for shared methods and fields to participate in inheritance.
This means that each class definition is going to have to carry around
some type of vtable pointing to all shared methods and fields of all
parent classes. Then when you call Derived.SharedMethod, the compiler
creates a call to Derived.SharedMethod rather than
BaseClass.SharedMethod, which means that Derived had better have that
definition some place. Derived.Shared is going to have to first run all
shared ctors up the inheritance tree, then send the actual method call
up the tree. That's bloat, performance issues, and I'm sure there's
some multithreading problems here as well (try to define exactly what
behavior you'd want here in a multithreaded environment).

Now, as a side note, notice that in VB.Net you can call shared members
through an instance reference (I think that's evil, but that's how the
language is defined). What's the compiler supposed to do in that case?
Call the declared type shared member, or are these members supposed to
be virtual (which opens another can of worms).

dim a As BaseClass = New Derived()
a.SharedMethod()
' who gets called?
Then, think about data rather than methods, since it makes no sense for
shared data to work differently. Right now, shared data exists in a
single class, and it's fairly easy to initialize the class definition
when the data is first accessed.

But do what you suggest, and what does that data look like in memory?
Now data is going to have to act like some kind of virtual method, since
an access to data through a Derived class must somehow redirect the
access to the base class (after tree initialization).
I realize the odds aren't good of anything
coming of it, but is there a place to go to formally bring this
issue to Microsoft's attention?


I'm sure there's a place, but keep in mind that very smart people have
thought about this stuff a long, long time.

Nov 21 '05 #8

P: n/a
In article <e8**************@TK2MSFTNGP12.phx.gbl>,
Gerald Hernandez <Cablewizard@sp*********@Yahoo.com> wrote:
Does this help to clear things up a little bit?


Yes, and thanks. I still think it makes logical sense for the
Shared constructor of a class to get triggered if a Shared method
of that class is invoked, but in fact -- for the reason you pointed
out, i.e., that there is only one classID variable, and the last
class to set it would "win" -- I would still have run into trouble
just a little way up the road. I basically wanted my base class
to do work using fields defined in my derived classes, and even
with instance methods you can't do that. So even though my idea
still seems logical to me I no longer have any examples of cases
where it would actually be useful, so maybe it is just not worth
the bother.
--
John Brock
jb****@panix.com

Nov 21 '05 #9

P: n/a
In article <sl******************@localhost.localdomain>,
david <da***@woofix.local.dom> wrote:
On 2005-09-21, John Brock <jb****@panix.com> wrote:

More and more this is looking like an easily fixable language design
flaw to me. Can anyone think of a reason why a Shared constructor
*shouldn't* execute if a Shared method is called before a class
has been instantiated?
This is actually a pretty good question, but the answer might be
complex. And I haven't really thought out all the permutations
involved. The problem with discussing vague language ideas like the
above is that as you try to define the behavior, each decision you make
creates a new complex topic to think through.

First, you really need to understand that what you're trying to do
is generally a considered a bad idea. It's not that anyone "puts
up with this limitation", it's that this situation doesn't usually
come up, because it's just not a good idea.

Next, the implementation is problematic. What you're really asking for
here is for shared methods and fields to participate in inheritance.
This means that each class definition is going to have to carry around
some type of vtable pointing to all shared methods and fields of all
parent classes. Then when you call Derived.SharedMethod, the compiler
creates a call to Derived.SharedMethod rather than
BaseClass.SharedMethod, which means that Derived had better have that
definition some place. Derived.Shared is going to have to first run all
shared ctors up the inheritance tree, then send the actual method call
up the tree. That's bloat, performance issues, and I'm sure there's
some multithreading problems here as well (try to define exactly what
behavior you'd want here in a multithreaded environment).

Now, as a side note, notice that in VB.Net you can call shared members
through an instance reference (I think that's evil, but that's how the
language is defined). What's the compiler supposed to do in that case?
Call the declared type shared member, or are these members supposed to
be virtual (which opens another can of worms).

dim a As BaseClass = New Derived()
a.SharedMethod()
' who gets called?
Then, think about data rather than methods, since it makes no sense for
shared data to work differently. Right now, shared data exists in a
single class, and it's fairly easy to initialize the class definition
when the data is first accessed.

But do what you suggest, and what does that data look like in memory?
Now data is going to have to act like some kind of virtual method, since
an access to data through a Derived class must somehow redirect the
access to the base class (after tree initialization).
I realize the odds aren't good of anything
coming of it, but is there a place to go to formally bring this
issue to Microsoft's attention?


I'm sure there's a place, but keep in mind that very smart people have
thought about this stuff a long, long time.


It really doesn't seem all that messy to me. First of all, most
classes don't even have Shared constructors, so most of the time
nothing different would happen. It's true that every shared method
would now have to test a flag somewhere to see whether its class
had been initialized, but how expensive can that be, given everything
else that is going on? Calling a chain of Shared constructors
would be a one time thing, so that wouldn't add any real cost
either. And you would *never* have to call a Shared constructor
when an instance calls a Shared function, because the appropriate
Shared constructor was already called the first time that class
was instantiated. So what am I missing? (OK, threads). It just
seems logical to me that when you explicitly call
MyDerivedClass.SomeSharedClass -- as opposed to calling
MyBaseClass.SomeSharedClass (which you can always do if that is
what you want) -- that the MyDerivedClass Shared constructor ought
to be invoked.

That said, I have to admit that what I was trying to do was in fact
a bad idea, so I can no longer claim to have been victimized by
bad design, and I'm more open to the possibility that maybe this
is *always* a bad idea. :-/
--
John Brock
jb****@panix.com

Nov 21 '05 #10

P: n/a

"John Brock" <jb****@panix.com> wrote in message
news:dg**********@reader1.panix.com...
:
: In article <yq********************@twister.southeast.rr.com >,
: _AnonCoward <ab*@xyz.com> wrote:

<snip>

: Actually you missed the point of my question.
I thought I might have when I submitted my response. Still, I figured I
offer what help I could and hope for the best.
: I was interested in
: *Shared* methods, and getting the class to initialize itself via
: the Shared constructor without actually having to create any
: instances of the class.
This was the root of my confusion. I did not realize you could call a
constructor without creating an instance of a class.
: .NET seems determined to disallow this.
: I had already tried using Shared properties, but .NET won't allow
: Overrides and Overridable with Shared properties, and using Shadows
: on the property in the derived class doesn't fix the problem (i.e.,
: the Shared constructor still isn't called).
:
: However I did find a workaround. If I give the derived class an
: empty Shared DoNothing method that the base class doesn't have and
: then call DerivedClass.DoNothing this *does* cause the Shared
: constructor of DerivedClass to execute, without the expense of
: creating a class instance where one isn't needed.
That's a novel concept for me. What you are saying is, if a class
defines a shared constructor and a shared function of the class is
invoked, that constructor is also called. I was able to confirm this
behavior and I also discovered that a class can define (at least) two
parameterless constructors at once:
Public Class [class]
Shared Sub New()
End Sub

Public Sub New()
End Sub
End Class
I believe this is unique in that I know of no other circumstance where
two methods with identical signatures (parameterless in this case) can
coexist in the same class.

: It still means
: that I have to explicitly initialize the class though, which is
: annoying.
:
: More and more this is looking like an easily fixable language design
: flaw to me. Can anyone think of a reason why a Shared constructor
: *shouldn't* execute if a Shared method is called before a class
: has been instantiated? I realize the odds aren't good of anything
: coming of it, but is there a place to go to formally bring this
: issue to Microsoft's attention?
: --
This is of course outside my area of familiarity and I trust the more
knowledgeable answers you received have sufficed. While my reply did not
address your question, I at least have the satisifaction of having
learned a cool new trick. Thanx!
Ralf
--
----------------------------------------------------------
* ^~^ ^~^ *
* _ {~ ~} {~ ~} _ *
* /_``>*< >*<''_\ *
* (\--_)++) (++(_--/) *
----------------------------------------------------------
There are no advanced students in Aikido - there are only
competent beginners. There are no advanced techniques -
only the correct application of basic principles.
Nov 21 '05 #11

This discussion thread is closed

Replies have been disabled for this discussion.