Over the past few months I've had some requests to show how you can bind a custom object collection to a GridView. When looking deeper into the collections, I noticed that the developers were working way to hard to create their collection class. The collections were inheriting from System.Collections.Specialized.NameObjectCollectionBase and implementing IEnumerator, IEnumerable, & IUpdatable, etc to accomplish some simple tasks (ie: add, remove, for each loops, etc). When implementing these interfaces, the developers were manually having to wire everything in. On top of this, they were having problems binding to .NET controls. Another quick point to make here is that the specialized collection does type casting at run time.
What I proposed was to inherit from System.Collections.Generic.List instead. What this does is allow them to do their basic add, remove, sort, and manipulate their lists. It also is strongly typed and can be accessed by index. Generics provide better type safety and performance than non-generic collections (ie NameObjectCollectionBase mentioned above).
I'm going to create a simple vehicle collection and bind a GridView to it using the Generic.List.
Public Class Vehicle
Private _Make As String = String.Empty
Private _Model As String = String.Empty
Public Property Make() As String
Set(ByVal value As String)
_Make = value
Public Property Model() As String
Set(ByVal value As String)
_Model = value
Public Sub New()
Public Sub New(ByVal make As String, ByVal model As String)
_Make = make
_Model = model
Here is the vehicle class (object) that we'll reference in our collection. Now for the collection.
Public Class Vehicles
Inherits List(Of Vehicle)
Public Sub New()
Public Sub New(ByVal capacity As Integer)
Public Sub New(ByVal collection As IEnumerable(Of Vehicle))
You'll notice how we inherit from System.Collections.Generic.List and cast the collection as a type of Vehicle. It's as simple as that. I added 3 constructors for your own reference. Now all we have to do is add some data to the collection and bind a GridView to it.
Partial Public Class _Default
Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load
If Not Page.IsPostBack() Then
Private Sub GridView1_DataBind()
Dim myVehicles As Vehicles = New Vehicles()
myVehicles.Add(New Vehicle("Ford", "Mustang"))
myVehicles.Add(New Vehicle("Pontiac", "Grand AM"))
Me.GridView1.DataSource = myVehicles
On page load, I bind the GridView if it is not a postback. I create a new instance of the Vehicles collection and add 2 vehicles to it. I then simply set the data source of the GridView to the Vehicle collection and call DataBind(). Now, each public property will be mapped and shown in your GridView if you have AutoGenerateColumns="true" set. If you don't do this, you'd approach the custom column mappings the same way as with a DataTable, DataView, etc (TemplateField, Eval expressions).
CollectionDataBinding_Soln.zip (89.23 kb)
>>>>> Edit 8/21/2008 <<<<<
I found another article that relates to this post. It's a great reference as to the benefits of using generic collections. The article lists the following reasons why you should use generic collections.
- Readability and simplicity of your code. Let’s take the case of getting the first string in a list of strings. With generics you would declare List<T> myList = new List<T>(); and then say string firstString = myList just like working with arrays. This syntax is much more simple and readable than what you used to have to write which was ArrayList myList = new ArrayList(); and then string firstString = myList as string;
- Performance. Every time you add a value type to a non-generic collection you have to box it to make it an object and every time you retrieve a value type from a non-generic collection you have to unbox it back from object. Even with reference type you still need to cast back to the correct type when retrieving items.
- Working against new smaller Framework SKUs. In Silverlight we decided to remove all the concrete non-generic collections completely from the codebase. This is mostly because the Silverlight core managed libraries is set to be the smallest useful set of classes. It’s also possible that other future small frameworks will not have the non-generic collections in store. If you ever plan to write code for those frameworks — you should convert it to use the generic collections.
- Better type-safe libraries. If you are developing libraries to be consumed by 3rd parties you should most definitely use generic collections when possible. This would allow consumer of your libraries to quickly figure out what’s expected to be stored in the collections instead of having to guess or figure out from documentation.