A group blog from members of the VB team
OK, so when you're playing around with LinQ and all it's various additional bits, you really do get to have a bit of fun.
I've made this available simply because i enjoyed doing it. The basic idea is to time and then compare the duration of various 'IsPrime' implementations. The 'client' simply allows you to run various IsPrime implementations. The IPrime interface defines the basic structure of running the exercise, while BasePrime provides the majority of the required code. Then, three imlpementations are provided (I make no defense of their efficiency!).
The LinQ aspect to this is in two parts:
- The 'Run' implementation in the BasePrime class. There's only a very, very minor LinQ statement to do here, but I continue to find even the smallest LinQ query more exciting than it's alternate
- How we might expose the 'IsPrime' method. In the example, I expose IsPrime as a method on IPrime, but the initial idea i had was to use an extension method. Extension methods of course, allow me to define a method on my own class, but expose them in such a way that i can use them like they're an instance method on another class
If you look at this example, you might start thinking about these things:
- Is the implementation of IsPrime the best one? If this question takes your fancy, that's great. But honestly, it's not the objective I had when I wrote the example. I did come up with 3 implementations for IsPrime, solely to satiate my own curiosity. Clearly, the LazyPrime implementation is poor. If you try the other two implementations, their performance is of course, extremely similar. The 'permanent' implementation allows primes to be save to a file on disk. This would improve first run performance of the implementation, but because both this, and the 'Temporary' memory have a store for the primes, subsequent runs will be similar. Feel free to try out your own implementations, and send them back on this thread, to see who's got the best one. I've set up the interface and base class for you to use and everything, so you just need to rewrite the IsPrime method.
- What classes could IsPrime extend? This was the question I had in mind when I wrote the example. Here's some things to try out yourself and see how far you get. First, genericize the IsPrime method. Now, limit it to the set of things that would make sense for it to extend. This might be kind of hard. This begs the question, do we need an interface for numerics (a not-uncommon request), or alternatively, should we consider extending the capabilities of generics, so we can 'limit' it better? THe next question is, WITHOUT an interface to limit the application of IsPrime, how gnarly is the implementation of a generic IsPrime method, that recognizes 4-5 specific types? Try it out and see. Comments welcome
- Does the order in which the imlpementations is run, affect their performance? I tried this out myself, and over a few runs, couldn't see a difference. If you find a difference, then simply run a single type at a time
- What OTHER methods are interesting to start conceiving of for extension methods on basetypes? Should VB write these and supply them?
- What philosophy should be taken with regards to extension methods? Should we encourage them? While it might seem there could be a glut of them, we have to remember that you have to opt in to any assembly that has them. Myself, I'm a fan of them, but I'd love to hear other thoughts
To run the example:
- Start a new project, and add the supplied files. Ensure primes.txt has the 'Copy to Output Directory' property set to 'Copy if newer'
- Set the count to different sizes to see how the result vary
My personal take is that extensions are appropriate when they:
* make composition clearer -- they're not intended to allow you to gratuitously move the parens
* provide general usefulness, as any good framework should -- they extend the most general types that make sense, and don't implement some arcane, specialized variation of an operation
* rely heavily (exclusively?) on namespaces for packaging -- because there's limited (at least in C#) filtering of extensions in a namespace, method name collisions will be a problem because the implementing type isn't a disambiguator
I'd like to see all of those tacky Shared (static in C#) methods on System.Array converted to generic pseudo-instance extension methods.
I'd like to see a reflexive method on class types that just returns the instance (sounds useless I know but if you're using a with block on an anonymous instance 'With New SomeClass' it's pretty convenient.
I'd kinda like to see some of the VB runtime (Left, Right) methods turned into extension methods, especially if you could get some of those null tolerant string methods in there.
I'd like to see a strongly-typed IClonable interface though that has nothing to do with this topic (though you could hypothetically make an extension method to simulate this).
I'd like to see some extension methods on that god awful office 11 object model.
Why not can I use:
Select Case DirectCast(sender, Button)
Case Is OKButton : ...
Case Is ExitButton : ...
Case Is ExportButton : ....
Case Else : .....