I just went back and read one of yesterday’s posts, and I caught some grammar errors, typos, etc. As my time is limited when writing these posts, I usually don’t go back through and revise/edit the posts. While I try to write as properly as I can, all my posts will be first drafts. When I write an actual technical article, I will revise the article and correct any errors that my present themselves before publishing it.
Monthly Archives: April 2004
Web Matrix ClassBrowser vs. WinCV
One of the VS.Net tools is WinCV. I’m sure it’s short for Class Viewer. Juval Lowy, in his episode of MSDN TV, introduces WinCV as one of his tips and tricks. In my opinion, everyone who is doing ASP.NET development should have an installation of Web Matrix. Included in that 1.3MB download is a lightweight ASP.NET development tool sans intellisense or code-behind. More importantly, it comes with a program call Matrix ClassBrowser. In my opinion, this tool does a much better job of type discovery than WinCV. WinCV just displays a class outline. ClassBrowser will also do this, but it has several more powerful features. For instance, in ClassBrowser, if you aren’t sure what you are searching for, you can browse by namespace. The feature I use most is the search feature. I can search for a class. Then I can pick from the search results. Once the type is displayed, then the powerful features come into play. I can switch between class outline and description. I prefer the description view where it displays its inheritance hierarchy, and then there are two useful option: Search for types extending the type, and search for types that have this type as a field, property, or method.
Yesterday I posted about the collections built into the .Net Framework. I knew that there were collection based on IList and some bases on IDictionary. In ClassBrowser, I looked up IDictionary, and then searched for types extending IDictionary. I can not do this in WinCV. Searching for types extending this interface quickly returned the information I needed, and this type of search is not even possible in the SDK documentation. I think this is very powerful. Furthermore, ClassBrowser will allow you to view a class definition including members that are inherited from a base class. WinCV only shows the current class outline without inherited members. ClassBrowser can also show you private members if you desire to see them. Two other features I use often are 1: A link to the online MSDN documentation for this type, and 2: A link to the SDK documentation for the type. All in all, it’s a great tool, and I use it almost every day. The only shortfall of the tool is that it is based on v1 of the .Net Framework, so some types have changed, but most types are close enough that it doesn’t make any difference. The link to the SDK documentation for the current type does go to the v1 SDK that I have installed, so to jump over to the SDKv1.1 of the docs, I just have to type in “v1.1” after the “SDK” in the url. I would very much like to see a version of this tool that can search over v1.1 of the Framework and even v2 when it comes out. It’s a little puzzling because through a “customize” option, I can load in my own custom library assemblies, and ClassBrowser will look in those during a search as well, and I can explore my own types just as powerfully as .Net Framework types. Of course, the link to the SDK docs for my types is broken. 🙂
In conclusion, I highly recommend the Web Matrix ClassBrowser for type discovery and research.
My friend Noah has a blog – MVP C#
My friend Noah Coad has just started his blog, so look for good content.
Lost post (I wrote offline back in March when i had no connectivity at all)
12 March 2004
I’m still here in Iraq serving with the Army Reserve. I’ve been here almost a year, and I go home in a month. Today I spent all afternoon downloading the Longhorn preview from MSDN, and now that I have it, I’m installing it in a Virtual PC on this computer. Virtual PC is a great product. Great job, Microsoft! So Longhorn is projecting a 15 minute installation. That’s way better that all previous versions of Windows although win 3.1 and win95a has floppy disks which slowed the installation down as well.
To be honest, it’s kind of exciting to see the install GUI of the next windows. Now when I install Longhorn for real after it comes out, I’ll have seen it before and know what to expect. The best thing I ever did was buy that extra 512mb of RAM for my Dell Lattitude laptop. With 768MB of RAM, I can run XP Pro as the host as well as a fully functional Virtual install, so I should be able to fully test out this Longhorn preview. To anyone with 256MB of RAM doing any kind of software development, I highly recommend 512MB MINIMUM, but you already know that.
So here is how it is. I download the .iso file from MSDN, and all I do it set it as the Virtual PC CD drive, Virtual PC mounts the file, and it boots straight into the install. How cool is that? Longhorn setup then asks for the CD key and then goes to a settings page where you can set the computer name and where on the hard disk(s) you want Longhorn installed. It also shows some other default settings. After that, it goes to a screen for “Collection information and copying files needed for setup” This page takes most of the setup time. <add more here about how setup progresses>
I’ve read all the hype about Longhorn, Avalon, Indigo, WinFS, etc, and it all sounds pretty cool. From a development standpoint, the thing I am most excited about is XAML. VB6 and even WinForms requires controls to be placed on the form using grid coordinates. for web developers, the hardest thing to do is make a webform with absolute positioning. Now don’t get me wrong. For simple input forms, you probably don’t need to make the UI that flexible in its placement of controls, but for applications that display more dynamic text or content, absolute placement of controls can be a stumbling block. Web programmers have always been able to benefit from the flow layout of HTML. In my Web Forms, even though I have a choice of GridLayout or FlowLayout, I always choose FlowLayout because it’s more flexible. Anyway, back to XAML. This markup language will replace coorinate placement of controls in Longhorn winforms. Now you can more easily have dynamic content in your windows apps. Personally, I prefer web apps to win apps. Every business app is going to be a distributed app. Even if it’s as simple as editing customer data or entering an order. Even if it’s a VB6 front end, it will have to communicate with a server either running some COM components or *gasp* interacting directly with the database. Well I would put that app on a webserver in a heartbeat. You can make an interface that is so much more flexible AND now that society is used to the Internet and web pages, why force your user to learn your UI. . . just make it a web application, and they are already familiar with how a web UI works. You have buttons and links, textboxes and drop down lists. Now XAML will give you the flexibility of a web form with the ability to have complete control as the developer did with winforms (since XAML is the future of winforms).
Now I’ve heard the argument that Windows developers are worried that Microsoft is going to force them to recycle their skills as web developers, but that’s just not true. Honestly, how many of you windows developers actually typed in the coordinates of where to place your controls on the forms? I didn’t think so. You dragged them onto the form, and then you added code to make the parts of the form functional. Well if you don’t want to deal with XAML, then don’t. Just continue to drag and drop your controls and then add your code behind them. I’ll take a step further and adjust the XAML so that parts of my form can grow and shrink with dynamic content. I am very excited about XAML, but remember, it’s still years away. Heck, we can’t even write a .NET Windows app right now unless we have a corporate environment where we can guarantee that all the clients will have the .NET Framework installed. So will be the same with XAML. I’m hoping that Microsoft will build XAML into a service pack for XP or perhaps a Framework upgrade because I don’t see Longhorn proliferating as soon as 2007. I think XP is such a great operating system that a lot of companies won’t be able to justify upgrading so soon. Win98 to XP was a no-brainer, but now that knowledge workers DON’T have to reboot several time a day (perhaps once a week or less), XP is meeting the need of a lot of people. So here’s to Microsoft making an upgrade for XP that will allow XAML apps!
I look forward to Longhorn and XAML.
I’m tired of making strongly-typed collections
I use stongly-typed collections all the time for items that are going to be reused quite often. I have recently gone on an adventure to educate myself of what collection are available in the .Net Framework and how they differ. My current scenario had a need for a collection to store a pair of strings and retain the order with which I added them to the collection, and I need to be able to bind the collection directly to a list control. A dataset would be an overkill. Right away, I know I’m going to be dealing with a key-value pair. This automatically rules out all the collections based on the IList interface: ArrayList, StringCollection. Since I need a key-value pair, I need a collection based on IDictionary: Hashtable, HybridDictionary, ListDictionary, and SortedList. Not too many to choose from, but I refuse to extend CollectionBase for this tiny task that is isolated to one user control!
I began to explore the differences between these four collections that are all bases on IDictionary and all stored the key-value pair in a DictionaryEntry object. What is really important is the underlying data structure of the collection.
The Hashtable is meant to offer better-than-linear performance on lookups. The order of the items is not guaranteed, and, in fact, you can add some items, then immediately iterate through to print them out, and they will often be in a completely different order. Ok, Hashtable is disqualified.
They HybridDictionary works well for my purposes. . . only if the number of items is no greater than 10. This is because it’s “Hybrid”. With 10 items or fewer it implements a ListDictionary under the hood (see next section). As soon as you add the 11th entry, it switches to a Hashtable, and all ordering reliability goes out the window.
The ListDictionary meets the requirements. It stores a key-value pair, and it retains the order in which I add the items. It does this by implementing the linked list data structure internally. According to the SDK, the ListDictionary has better performance than a Hashtable up to 10 items, and then Hashtable becomes faster. The SDK also warns that the ListDictionary should not be used with many items where performance is an issue.
I also looked at the SortedList just to make my comparison complete. The SortedList behaves like a Hashtable in that you can use a key to look up the value, but you can also use the index to find the value. Internally it keeps two arrays sychronized: one array for the keys and one for the values. It sorts the entries when added, so the list is always sorted, hence the name.
When whidbey gets here, I won’t have to worry about strongly-typed collections anymore. I’ll be able to declare them generically. . . or is that specifically? 🙂 I can’t wait!
I love the SDK. Especially since I don’t have access to Google and my other online resources, I have used the SDK documentation so much! It is a wealth of knowledge that every .Net developer should reference.
To get back to the collections, I did look at the NameValueCollection, but it does not implement IDictionary. Also, I was not able to bind it to the list control in the way I wanted. If I juse specified the source and then hit the “DataBind()” key [:-)], it would bind the list with the key value for the text as well as value. But I need to set the DataTextField and DataValueField. With IDictionary-based collections, “Key” and “Value” work, but the NameValueCollection returns a single string, not a DictionaryEntry object, so this presents a problem in getting the value in a binding situation. Sure, I could iterate through it and get the keys and values, but I’m just databinding, so I had to rule out this collection.
Finally, I chose the ListDictionary for my purposes. Then I started thinking that is some cases, my key-value set could become large, so I can’t use the ListDictionary. I might have to write one more strongly-typed collection. But for now, I’ll use an ArrayList of DictionaryEntry objects. How’s that for thinking outside the box? The ArrayList will grow dynamically and keep my items in a specific order because of the IList interface, but I can bind the key and value because the object being stored is a DictionaryEntry object. I think I’ll call it DictionaryList. So one more time, I have to extend CollectionBase (it’s internal data structure is an ArrayList). Normally I could extend the DictionaryBase class, but internally it uses a Hashtable which doesn’t guarantee order. And I’m back to strongly-typed collections. . . but this one I’ll reuse over and over and over and over.
public class DictionaryList : CollectionBase
{
public DictionaryEntry this[int index]
{
get{ return((DictionaryEntry)List[index]);}
set{ List[index] = value;}
}
public int Add(object key, object value)
{
DictionaryEntry entry = new DictionaryEntry(key, value);
return List.Add(entry);
}
//rest of class truncated.
}
Ahh, the answer to so many of my problems! Now it’s so simple to pop a few items in and then bind to a list control:
list.DataSource = myDictionaryList;
list.DataTextField = “Key”;
list.DataValueField = “Value”;
list.DataBind( );
list.SelectedValue = myValue;
Possible bug in ASP.NET 1.1?
I’ll preface this post by saying that I don’t have constant connectivity to the Internet from where I am right now. Every morning I wake up at 4:45AM, walk 1/2 of a mile to a satellite Internet Cafe run by some Arabs, and pay $6/hour to hook my laptop up to the Internet. Imagine 1 hour of Internet per day, and you can calculate that monthly bill and compare it to your cable modem bill. I use Net2Phone and for $.02 per minute, I can talk to my wife over the Net.
The point of that preface is that it’s hard to do some immediate Internet research into this issues, but here it is:
I have a page that has a user control containing a form. The form uses some of the validation controls with client script enabled. Everything works great. The form got a little long, and sometimes the length of one of the grids causes the page to scroll, and the save button is at the button. I turn on SmartNavigation to remedy the post-back-lose-scroll-position problem, but now, instead of posting back, some of the buttons will erroneously trigger the client validation script to fail even though input values are valid. I turn off SmartNavigation, and everything is perfect. Very frustrating. I’m wondering if the two features have a javascript conflict because I also get a javascript error when this occurs. I’m wondering if anyone else in the ASP.NET community has experienced this and if there is a workaround.
Making a page’s base class an abstract class.
In the normal code-behind technique, your page inherits from this regular class you create as the code-behind class. I’m implementing a template feature in my project, and most templates will be just markup without code, so there is no need for a code-behind class; however, I wanted to make sure every template implemented two properties, so I thought, “I’ll use an abstract class”. I created an abstract class and inherited my pages from it. It worked great, but I had a problem with the VS.NET designer. I can view the Template page in the designer because “the designer can’t create an instance of an abstract class”. Then I thought, “what benefit am I getting by making this base class abstract? Not much. If I make it a regular class, I can implement virtual, default values. So that’s what I did.
Lesson learned: Code-behind classes need to be non-abstract so the designer can function properly.
Post-back mania
We have a new, great post-back model with ASP.NET. In fact, I was using a similar model in ASP 3. I would choose a course of action based on a querystring or form value. I would post information back to the same page with an “action” querystring that described what to do next. The model worked well then. Now we have that model implemented for us. With any new capability comes the question: “When should I use it?” Certainly not all the time. I can pass XML to SQL Server, but does that mean that I should do it for every single stored procedure now? Certainly not!
I am currently working on a page that modifies certain properties. To save the data, I have a button that posts back, and I save the information. I have a cancel button. Should I use a postback with the cancel button? When the user cancels, I just want to leave this page and discard any changed information. I really don’t have any clean-up processing for this instance. I could post back and do a Response.Write( ) or Server.Transfer( ), but do I really need to reload that whole form, and then execute the button event handler to leave the page? That would be extra, unnecessary processing. No, instead, I’ll just have the button do a javascript onclick event that modifies the “location.href”. No unnecessary post-back. More efficient.
There have been several times where a simple hyperlink was much better suited for a task than a post-back. Also, remember that post-back handling comes after the Init and the Load events. So on a post-back, you reload all the old data before the post-back handling occurs. In some cases, I pass a querystring value to a page so that it knows what it needs to do right from the start. I can start doing work in the Init so that my usercontrols have the information they need in thier Load events.
As with all new capabilities comes the design decision of when to use them. With the up-coming Yukon release of SQL Server, I see some people putting all their business logic with the database’s CLR. Again, we will have to really analyze when it is appropriate to write some managed code at the database. Certainly not all the time.
Even when new capabilities surface, remember tried-and-true methods that have worked for years.
Outsourcing IT Jobs and the Development job market.
I’m listening to Bob Reselman on .Net Rocks right now, and some very interesting points were brought up. First is the outsourcing of IT jobs to India and other places where developers will work for fewer dollars. The company for which I work has partially done that, and half of my development team is actually in India. The guys over there do excellent .Net work, and they are very intelligent. We tasked them to write a module, and the result was fabulous and met the specs exactly. The problem with outsourcing to a foreign country is that the customers are still here in the U.S. There has to be someone to translate from the customer’s need to the technical specs and then actually code to those specs with the customer’s needs in mind. The developers in India just can’t do that. They can do pieces that we delegate and monitor, but in order to produce a quality product, American developers are still needed to pull it all together and make a package that is geared to the customer. I imagine that some IT departments think only with their wallets, but then they fail to estimate the added cost of communication. Outsourcing development creates a huge communication barrier, and that will cost money. There will need to be more code and feature reviews to ensure the project is on track. The communication barrier is very real and very expensive, so I predict that some companies that are quick to outsource to India will come back and learn that they need hometown developers as well, and they will lose money for jumping on this bandwagon instead of save money.
I know that plenty of software developers are out of work now or are working for less money than they feel they deserve. I know it’s tough in parts of the country. More now than ever, we must all take responsibility for our careers and for providing for our families. Yes, it’s a greater challenge now, but the laws of supply and demand are working. We must improve our skills so that we are more in demand. In this market, a developer cannot coast and hope to find a nice, tidy, well-paying job. There is more competition. Competition is good. That is what our economy is based on. I’ve been away from my development job for over a year while deployed to Iraq, and I have some catching up to do if I am to stay competitive. I’m going to have to put the nose to the grindstone because there are people out there eyeing my job. It’s up to me. . . and you.
MVP Global Summit and my friend, Noah Coad
A week ago, I emailed Noah Coad (Texas A&M student and C# MVP), and I inquired if he was attending the MVP Conference. He emailed me back from the Summit, and he had included notes from several other MVPs that he met at the conference. I’m compelled to include the E-mail here:
From Noah Coad:
Hey Jeff! As always, it’s great to hear from you! Yes, in fact, I’m here
in the hotel up in Seattle right in the middle of the MVP Global Summit!
You’d never guess who I’m sitting here hanging out with late in the hotel
lobby… They all wanted to say hi! We all appreciate your dedication
there in Iraq. Check below… I’ll post my reply to your message below.
🙂
————-
Hey Jeff,
Mark Dunn here. Noah tells me you are a big fan. Glad u enjoy the .Net
Rocks shows. Just wanted to say hello and wish you well. Drop me a line
sometime.
Cheers,
-Mark
———-
Jeff,
You may not know Keith Nicholson, but I’m a big fan of yours. Thanks for
serving our country. It’s good to know you have a great friend like Noah
keeping up with you. I hope you get a lot of time programming. Hope to see
you at a MVP program in the future. If you or any other developers want to
chat, feel free to contact me.
Peace,
Keith Nicholson
———-
Hey Jeff,
You know you’re now famous with the MVP crowd. Who knew one email would
vault you into stardom! Although I’m a Canadian I want to say thanks for
what you’re doing over in Iraq. Keep safe and keep up with your development
skills… .NET Rocks!
Rob Windsor [MVP-VB]
Toronto Visual Basic User Group
—————
Hey, Jeff –
I came downstairs to grab a glass of water, and then I got caught up in a
conversation with a few geeks when one of them spoke up and said that he
knew you.
So, I’m Rory (.NET Rocks), and just wanted to say that Carl and I have
really enjoyed your letters. It blows us away that you’re off on the other
side of the planet and listening to the show. You’re a true fan, and we
honestly appreciate it 🙂
Write to us whenever you feel like. We seriously enjoy hearing from you.
Talk to you later,
– Rory
—————
Jeff:
Jon Box here. Thanks for protecting our country and keep sending those
updates to .NET Rocks. I think you should send a picture to those guys and
start a blog. It would get a bunch of hits. Anyway, stay safe and hurry
home.
Jon Box
Hello Jeff,
Hi from another MVP here at the summit in Seattle. Stay safe.
David Totzke
Chair, Marketing and Sponsorship
International .NET Association
—————
Wow. I’ve heard a lot of these names from .Net Rocks and from reading blogs, so I’m eager to get back to the states and maybe meet some of you who replied at a development conference.