Welcome to McFunley.com Sign in | Join | Faq

No True Object Programmer, Part Deux

posted on Sunday, February 27, 2005 6:32 PM by mcfunley

Edit (2/28): What I have to say about raising an event asynchronously in VB is very incorrect. If you got here by googling “raise event async VB“ (or thereabouts), do not listen to me. Read Bill McCarthy's comment about it.

 

------------------------------------------

 

Well, Bill loves VB.NET, and knows a lot about it. I am in a slightly different camp, in that I (arguably) know a lot about it because I am forced to use it at work, but I haven’t grown to love it very much.

 

But as to your difficulty in parsing VB.NET code, well as you said, VB.NET is actually more natural. It is probably more that you need practice reading and writing the code.

 

I concede that this is probably true. I’ve been staring at C/C++/Java/C# since I was 11 years old, so it’s quite likely that’s the only reason I find it more natural. It doesn’t really help that I switch between VB.NET and C# projects on an almost hourly basis these days. I’ll jump to the VB project and start typing:

 

StringBuilder sb = …

 

Whoops. Wrong one. Apparently I can’t make the jump as effortlessly as the woman shouting into a cellphone on the train next to me last week weaved an intricate and impressive unbroken stream of Spanish/English (“Spanglish?”).

 

So yes. Readability is probably a personal problem.

 

This started out, I guess, as a discussion about which language was “more OO.” That’s may be a vague metric, so I’ll try to limit the discussion here to which language lets you accomplish the task at hand in the simplest possible way with minimal connectivity and shared knowledge between your objects.

 

In the case of events, I think that at best, this is a draw. This is an opinion.

 

VB wins when it comes to a few useful abstractions: the RaiseEvent keyword, and declarative event handling (the WithEvents/Handles keywords).

 

In a comment on Bill’s blog, I referred to these as “leaky abstractions” (to borrow shamelessly from Joel). What I mean by that is, they work beautifully in the simple cases, but in more sophisticated situations they break down and you’re forced to understand what is actually going on. VB may or may not leave you with a way out, once you’ve done the learning bit.

 

My first example here was raising an event asynchronously. Here is code that accomplishes calling event handlers on another thread in C#.

 

internal class MyClass

{

public event EventHandler MyEvent;

 

protected virtual void OnMyEvent(EventArgs e)

{

                  this.MyEvent.BeginInvoke(this, e, null, null);

}

}

Here is code that accomplishes the same task in VB.NET.

 

    Friend Class SomeClass

        Public Event MyEvent As EventHandler

        Private Delegate Sub EventRaiserDelegate(ByVal e As EventArgs)

 

        Protected Overridable Sub OnMyEvent(ByVal e As EventArgs)

            RaiseEvent MyEvent(Me, e)

        End Sub

 

        Protected Overridable Sub OnMyEventAsync(ByVal e As EventArgs)

            Dim del As EventRaiserDelegate = AddressOf OnMyEvent

            del.BeginInvoke(e, Nothing, Nothing)

        End Sub

    End Class

 

Bill’s correct, you can raise an event asynchronously in VB.NET, albeit in a roundabout way. Unless there's a radically different method I haven't thought of, I need to write and then call OnMyEventAsync, which calls a traditional event raiser on another thread.

 

Here is where I think the claim that VB is “more OO” breaks down. The representation of the event as a list of functions (which is what C# gives you) was significantly simpler for us in this case. We got the job done with less code, so in my mind C# wins the OO battle here.

 

As to events in Vb.NET, I'm sorry but there is no "inadvertant GC rooting". I don't know who told you that, but you/they were sorely mislead.

On serialization, Vb.NET has absolutely no problems with XML serialization. There is however an issue with binary serialization and MarshalByRef classes. The real problem is MarhsalByRef classes, eg a Windows.Form, cannot be binary serialized. If you need to work around that, you can do so in Vb.NET 2005, and more elegantly than C#.

 

Poor terminology on my part, I guess. What I was referring to with “GC rooting” was the situations where a programmer attempts to dereference an expensive object so that it may be collected. A common mistake is leaving events wired up (and hence, a reference that has a gc root).

 

Is that any more difficult to deal with in VB than it is in C#? No, not really. Touché. But am I justified in calling an event a “leaky abstraction” if they require a deeper understanding of function pointers and GC in order to keep your program from hogging memory? I think so.

 

So that leaves the last sitch: serialization. MarshalByRef is actually not what I was thinking about, but it’s closely related. MarshalByRefObjects are at least serializable, and unless you are persisting to a storage medium you will succeed in serializing a graph if your only mistake is having a ObjRef going along for the ride.

 

Objects that are not [Serializable()] at all are a bit more problematic. You’ll get an exception which will be difficult to track down if you have event handlers wired up to any of these. C#’s got an easy way out (google it; my post is getting really long, dammit). The hacks VB will force you into in some cases is likely to make you cry. I know it made me cry.

 

So which language is “more OO?” That’s impossible to answer objectively, and it probably makes no sense to even try, but I’ll tender a personal opinion.

 

My feeling is that VB gives you some keywords that are useful for simple OO. Unfortunately, it obscures some of the underlying nuts and bolts, and this gets in the way of your own attempts at OO abstraction. C#, on the other hand, is a little better at ensuring that the realities of the CLR are quickly accessible if you need them.

 

In an ideal world, we’d have both in one language. But forced into a choice, I’ll opt for seamless access to the guts. Keeping my own objects as loosely coupled as possible is what I’m most interested in doing.

Comments

# re: No True Object Programmer, Part Deux @ Sunday, February 27, 2005 6:42 PM

Clarification of, "I’ve been staring at C/C++/Java/C# since I was 11 years old" -- in that order. Several of them didn't exist in 1990.

  Dan McKinley

# re: No True Object Programmer, Part Deux @ Sunday, February 27, 2005 8:26 PM

Dan, Dan, Dan, Dan Dan ;)

Did you ever stop to try the folowign code ??

Friend Class SomeClass

Public Event MyEvent As EventHandler

Protected Overridable Sub OnMyEvent(ByVal e As EventArgs)
MyEventEvent.BeginInvoke(Me, e, Nothing, Nothing)
End Sub

End Class


Would you like some salt with your hat ?

  Bill McCarthy

# re: No True Object Programmer, Part Deux @ Sunday, February 27, 2005 8:49 PM

Dan,

Re:
<quote>
What I was referring to with “GC rooting” was the situations where a programmer attempts to dereference an expensive object so that it may be collected. A common mistake is leaving events wired up (and hence, a reference that has a gc root).

Is that any more difficult to deal with in VB than it is in C#? No, not really. Touché. But am I justified in calling an event a “leaky abstraction” if they require a deeper understanding of function pointers and GC in order to keep your program from hogging memory? I think so.
</quote>


I think you really need to have a hard look at this one too. VB.NET provides abstractiosn that make this cleanup really simple and across the board far mroe elegant and robust. But I won't spoil the suspense on that one for you today, instead I'll let you think about it for a bit. Let's see if you can beat me to it :)

Watch my blog in the next couple of days and all will be revealed :)





  Bill McCarthy

# re: No True Object Programmer, Part Deux @ Sunday, February 27, 2005 9:07 PM

"Would you like some salt with your hat ?"

Yes, please. This is the "radically different method I haven't thought of" that I so cowardly left room for. Well done.

Looks like Intellisense can't teach you everything.

  Dan McKinley

SKIN NAME : ImageHeader