2009-10-16

Reference types

Quick reminder: Any object you have to instantiate (e.g. create with the new keyword) is what’s called a Reference Type. It means that, when used as a method parameter, it will always be treated as a reference parameter (ref in C#, ByRef in VB).

In other words, this is redundant:

  1: void ModifyData(ref DataSet data)
  2: {
  3:     //....
  4: }

Because DataSet is a reference type, the ref keyword in the above examples serves no use. 

Opposite to reference types are Value Types, like an int or a string. They have to specify the ref keyword in the parameter if they want to be treated as such.

Here’s a good article on reference and value types.

See ya.

2009-10-14

Setting an enum value from a string

In a piece of code I was reviewing I saw that they wanted to set the value for an enum from a string, and what they did was to create a large method with a big switch statement, setting the correct enum value for each case. Something like:

  1: enum Operators
  2: {
  3:    GreaterThan,
  4:    Equals,
  5:    LessThan
  6: }
  7: 
  8: Operators GetOperatorFromString(string s)
  9: {
 10:    switch(s.ToUpper())
 11:    {
 12:       case "GREATERTHAN":
 13:          return Operators.GreaterThan;
 14:       case "EQUALS":
 15:          return Operators.Equals;
 16:       case "LESSTHAN":
 17:          return Operators.LessThan;
 18:    }
 19: }

Now, this could be kind of simple if your enum doesn’t have many values, but if we’re talking about very large lists, then we have a problem…

Well, the solution for this is actually very simple, by using System.Enum.Parse, which has the following signature:

object Enum.Parse(System.Type enumType, string value, bool ignoreCase);

So, you can write the following:

  1: enum Operators
  2: {
  3:    GreaterThan,
  4:    Equals,
  5:    LessThan
  6: }
  7: 
  8: // ...
  9: 
 10: Operators o = (Operators)Enum.Parse(typeof(Operators), "greaterthan", true);

Notice that, since we have the ingnoreCase parameter set to true,  we can use the string in any kind of case. If the string value doesn’t match any of the enum values, an exception of type ArgumentException will be raised.

2009-10-06

Quick Windows tips

This has nothing to do with programming, and probably many people already know it, but what the hell. It might be a nice thing to teach your end users.

First, to get a screenshot of just the active window, instead of your whole screen, just press the Alt and PrintScreen keys together. That way, you’ll copy the screenshot to your clipboard, but you’ll not get your task bar, and you wouldn’t have to go to Paint to chop your image.

Second, to get the text of a message box shown by an app, just make sure that box is active, and press Ctrl + C. Windows will automatically copy the title, message and buttons text to the clipboard. You’ll get something like this:

---------------------------
Exit
---------------------------
Are you sure you want to quit?
---------------------------
Yes   No  
---------------------------

2009-09-18

Difference between Eval and Bind databinding expressions

Hi. I just faced a problem where I was using an ASP.NET GridView control which was bound to a SqlDataSource. One of the bound columns was “User” and, of course, brought the user name. What I wanted to do was to add a HyperLink to that text, so that instead of just saying “Mark”, with would show up as a link to the UserDetalis page, passing “Mark” as a QueryString variable. Something like this:

  1: <a href='UserDetails.aspx?user=Mark>Mark</a>

So, because I had a databound GridView, I just had to make the “User” column a template column and replace the standard label (Label1 in this code)

  1: <asp:GridView ID="myGridView" runat="server" 
  2:     DataSourceID="myDataSource">
  3:     <Columns>
  4:         <asp:TemplateField HeaderText="User" SortExpression="User">
  5:             <ItemTemplate>
  6:                 <asp:Label ID="Label1" runat="server" Text='<%# Bind("User") %>' />
  7:             </ItemTemplate>
  8:         </asp:TemplateField>
  9:     </Columns>
 10: </asp:GridView>

by a HyperLink (HyperLink1 in this code), and set its NavigateUrl property to the new value, which held the whole hyperlink HTML text. So the first thing that came to my mind was to do something like this:

  1: <asp:HyperLink ID="HyperLink1" runat="server" Text='<%# Bind("User") %>'
  2:     NavigateUrl='<%# String.Format("UserDetails.aspx?user={0}", Bind("User")) %>' />

But it turned out I got a runtime error that said: The name 'Bind' does not exist in the current context. If I used Eval instead of Bind:

  1: <asp:HyperLink ID="HyperLink1" runat="server" Text='<%# Eval("User") %>'
  2:     NavigateUrl='<%# String.Format("UserDetails.aspx?user={0}", Eval("User")) %>' />

It worked like a charm.

OK, I got my problem solved, but now I needed to know the difference between both, and specifically why it worked with one and not the other. Well, here it is:

Eval is one way, for read-only purposes, as Bind is two way, for read-write operations. Eval is actually a static protected method defined on the TemplateControl class, from which the Page class is derived, and it returns a string. Because it’s a real method, you could combine it with other statements, like the string.Format we just used. Bind, on the other hand, is not an actual method, it’s a new ASP.NET 2.0 databinding keyword, so of course, it can’t be used with other method calls or stuff. Bottom line is, if you need to only read the text, and perhaps change it a little, use Eval. If you need to write back to the db or something like that, use Bind.

Hope you got it clear. This article has some more deep definitions, which you might find useful as well.

2009-09-15

Creating design-time compatible properties and events, part 2

Hi all. In part 1 of this article, we learned how to make our simple properties show up in the properties window at design-time, so that they looked just like the built in ones that .NET controls have. Here, in part 2, we’ll discuss how to make your events show up, as well as some more advanced stuff, like adding custom lists.

First, events, opposite to Properties, don’t show by default in the properties Windows (that is, they’re not Browsable by default), so in order to show them all we need to do is to set that property to true:

  1: [Browsable(true)]
  2: public event EventHandler MyEvent;

It’s all it takes.

Now, the fun part. Let’s add some custom lists. Suppose we want to add a property to our NiceTextBox called SomeList, which can hold any of these four values: One, Two, Three and Four. There are several ways to achieve this, but I’m gonna take the simple way and use a string. So, first, we’ll have to create a “converter” class. Converter classes are used to convert specific types to and from other different types. Since we’re using a string, we’ll need to create a class that inherits System.ComponentModel.StringConverter. We’'ll use this to convert my list to and from a string.

  1: public class SomeListConverter : StringConverter
  2: {
  3:     //Values list. You could bring this from a database or so
  4:     private readonly string[] values = new[] { "One", "Two", "Three", "Four" };
  5: 
  6:     public override bool GetStandardValuesSupported(ITypeDescriptorContext context)
  7:     {
  8:         //When true, only a value from the list can be selected
  9:         return true;
 10:     }
 11: 
 12:     public override StandardValuesCollection GetStandardValues(ITypeDescriptorContext context)
 13:     {
 14:         //Return the list as a collection of standard values.
 15:         //This is the method the designer will use to pupulate the list
 16:         return new StandardValuesCollection(values);
 17:     }
 18: 
 19:     public override bool GetStandardValuesExclusive(ITypeDescriptorContext context)
 20:     {
 21:         //When false, the list will be editable, meaning that the user could type 
 22:         //a value as well. When true, the list will be read-only
 23:         return true;
 24:     }
 25: }

Now, let’s create the property. We’ll have to use the TypeConverter attribute to tell the property what class it should use to convert our List (of type StandardValuesCollection) to and from a string:

  1: [TypeConverter(typeof(SomeListConverter))]
  2: [Category("Custom properties"), DefaultValue(""), Description("Some custom list used")]
  3: public string SomeList { get; set; }

The result will be pretty neat:

OK, so that’s it for simple lists. But what if one of our custom properties needs to be set through a more complex class? Let’s take a look at the following example, we’ll create a property called Version, which will have all four parts of a regular assembly version: Major, Minor, Build and Private. We’ll do it so that the user can set the version value directly (something like 2.1.0.17), or he can set the value for each part separately. That kind of behavior, like the one we see in common properties as Location and Size, is achieved through something called expandable objects, specifically by using the ExpandableObjectConverter class.

First, we’ll create an ApplicationVersion class:

  1: public class ApplicationVersion
  2: {
  3:     public short Major { get; set; }
  4: 
  5:     public short Minor { get; set; }
  6: 
  7:     public short Build { get; set; }
  8: 
  9:     public short Private { get; set; }
 10: }

This class we’ll represent the type of our Version property (which we’ll construct later). Now, we’ll have to create the converter. Like said before, because this property will be an expandable object, we’ll have to inherit the ExpandableObjectConverter class:

  1: internal class ApplicationVersionConverter : ExpandableObjectConverter
  2: {
  3:     public override bool CanConvertTo(ITypeDescriptorContext context, 
  4:         Type destinationType)
  5:     {
  6:         //This will indicate if the Converter can convert the object TO the 
  7:         //specified type. In this case, ApplicationVersion to string
  8:         return destinationType == typeof(ApplicationVersion) || 
  9:             base.CanConvertTo(context, destinationType);
 10:     }
 11: 
 12:     public override bool CanConvertFrom(ITypeDescriptorContext context, 
 13:         Type sourceType)
 14:     {
 15:         //This will indicate if the Converter can convert the object FROM the 
 16:         //specified type. In this case, string to ApplicationVersion
 17:         return sourceType == typeof(String) || 
 18:             base.CanConvertFrom(context, sourceType);
 19:     }
 20: 
 21:     public override object ConvertFrom(ITypeDescriptorContext context, 
 22:         System.Globalization.CultureInfo culture, object value)
 23:     {
 24:         //This will implement the logic to convert from string to object. 
 25:         /It will be used when the user directly enters the version value 
 26:         //(2.0.4.17) instead of setting each part individually
 27:         if (value is string)
 28:             try
 29:             {
 30:                 string s = value.ToString();
 31:                 string[] versionParts = s.Split('.');
 32:                 if (versionParts.Length > 0)
 33:                 {
 34:                     var version = new ApplicationVersion();
 35:                     if (versionParts[0] != null)
 36:                         version.Major = Convert.ToInt16(versionParts[0]);
 37:                     if (versionParts[1] != null)
 38:                         version.Minor = Convert.ToInt16(versionParts[1]);
 39:                     if (versionParts[2] != null)
 40:                         version.Build = Convert.ToInt16(versionParts[2]);
 41:                     if (versionParts[3] != null)
 42:                         version.Private = Convert.ToInt16(versionParts[3]);
 43:                     return version;
 44:                 }
 45:             }
 46:             catch (Exception)
 47:             {
 48:                 throw new ArgumentException(
 49:                     string.Format(
 50:                         "The value {0} isn't a valid Version number", value));
 51:             }
 52:         return base.ConvertFrom(context, culture, value);
 53:     }
 54: 
 55:     public override object ConvertTo(ITypeDescriptorContext context, 
 56:         System.Globalization.CultureInfo culture, 
 57:         object value, Type destinationType)
 58:     {
 59:         //This will implement the logic to convert from object to string. 
 60:         //It serves the exact opposite purpose of the above method
 61:         if (destinationType == typeof(string) && value is ApplicationVersion)
 62:         {
 63:             var version = (ApplicationVersion)value;
 64:             return string.Format("{0}.{1}.{2}.{3}", version.Major, 
 65:                 version.Minor, version.Build, version.Private);
 66:         }
 67:         return base.ConvertTo(context, culture, value, destinationType);
 68:     }
 69: }

Finally, we’ll just create our Version property:

  1: [TypeConverter(typeof(ApplicationVersionConverter))]
  2: [Category("Custom properties"), DefaultValue("0.0.0.0"), Description("App version")]
  3: public ApplicationVersion Version { get; set; }

Here’s what we’ll get:

So, it’s possible to create properties and events that are fully design-time compatible. It might take a little work, but it’s definitely worth it, specially for people that create custom controls and plan to share or sell them. Hope you enjoyed the articles.

2009-08-12

Creating design-time compatible properties and events, part 1

We all create custom or user controls and classes all day and, of course, custom properties and events. Well, whenever you create you own control, it’s properties are automatically show in the property window at design time. But our properties don’t look the same as the built in ones for objects, right? Those have got categories, descriptions, lists with custom values, and so on. And for custom events, they don’t even show up!

In this two part article, I’ll be showing you how to make your properties and events more “developer friendly” (nice term, right?). In part 1, I’ll be talking about simple properties, and in part 2 we’ll get to events and custom lists.

This is what any built in property for, let’s say, a TextBox looks like:

 

We got:

  1. A category
  2. A custom list, which provides from an enumeration
  3. A description of what the property does

We can get that for our properties and events as well, so first, to continue with the example, let’s create or custom TextBox, which will basically be a class that inherits from the TextBox class, and add a couple of properties:

  1: public partial class NiceTextBox : TextBox
  2: {
  3:     public string SomeString { get; set; }
  4: 
  5:     public int SomeInt { get; set; }
  6: }

Nice. Compile and add a NiceTextBox control to the form. Our two very clever properties will show in the Properties Window, but they’ll be under the “Misc” category (meaning they don’t have a category at all), and they will have no comment:

  

In order to make our properties “look” that way, we need to use a concept called Attributes. Attributes provide a powerful method of associating declarative information with C# code (types, methods, properties, and so forth). In our case, these attributes will “kinda” represent the metadata used by the designer in the properties window.

So, to create a category for our couple of properties, will use the “Category” attribute, like this:

  1: [Category("Custom properties")]
  2: public string SomeString { get; set; }
  3: 
  4: [Category("Custom properties")]
  5: public int SomeInt { get; set; }

Here’s what we’ll get:

Of course, the category name, which is the one in double quotes, can be anything, and it doesn’t have to be the same for all properties.

Just as the Category attribute, we can get a lot of things by using more of them, here’s a few:

  • DefaultValue – Value to set for the property by default
  • Description – Description of what he property does
  • ReadOnly – Indicates if the property can be changed at design time in the properties window. It can still be changed via code though. By default, this attribute is false.
  • DisplayName – The name to show in the properties window
  • Browsable – Indicates if the property should be shown at all at design time in the properties window. When set to false, it won’t be visible, although you can still access it at runtime, in your code. By default, this attribute is true, except for events, which is by default false.

So, let’s elaborate our properties a bit more:

  1: [Category("Custom properties"), Description("Some string used")]
  2: public string SomeString { get; set; }
  3: 
  4: [Category("Custom properties")]
  5: [Description("Some number used in the NiceTextBox")]
  6: [ReadOnly(true)]
  7: [DisplayName("SomeNumber")]
  8: public int SomeInt { get; set; }

Notice that, in the first property, SomeString, we set all attributes in the same line, separating them by commas, and in the second property, SomeInt, we did it in different lines. Both approaches are valid. So, this is what we get:

As put in our attributes, we included a description for both properties. In addition, SomeInt property will be read-only at design time, and will be shown as SomeNumber.

Of course, there are a lot more attributes than the ones I listed, but I hope you get the general idea. In part 2 of this article, I’ll be showing you some more advanced features. See you then.

2009-08-05

The String.Format method

Believe it or not, one of the most powerful classes in the .NET Framework is the String class. Yep, you read it right, the String class. It has about ten millions uses, and every other class can be converted to one.

The String class also has some pretty cool methods: String.Contains and String.IsNullOrEmpty are two of my favorites, no to mention a whole other bunch of methods that every programmer uses on a a daily basis: Substring, CompareTo, IndexOf, Replace, and so on. The list is pretty huge, and they all have great uses. Specially the String.Format method, which is what I’ll talk about in this post.

Many .NET developers use String.Fomat, but from my experience, most of them only use it to concatenate strings in a more fancy, readable way. So, instead of writing this:

  1: string s = "Your name is, '" + name + "' and your age is " + age;

They’ll write this:

  1: string s = string.Format("Your name is '{0}' and your age is {1}", name, age);

What tat line says is “replace the {0} symbol with the first variable and the {1} symbol with the second variable” (and so on). Even though that’s a good start, and it’s a better solution performance-wise, there’s really a lot more we can get from the String.Format method. Take a look at this example (the dots at the beginning and end of the string are just for reference):

  1: string.Format(".{0,10}.", "right") //".     right."

Here we also have the {0} symbol, which will be replaced by the first variable, “right” in this case, but we’re also telling the method to fill with blank spaces the rest of the string until it reaches 10 characters long. The positive 10 indicates that the variable text should be placed to the right of those spaces. So if used a negative number, we’ll get the variable value to the left:

  1: string.Format(".{0,-10}.", "left"); // ".left      ."

We could also format numbers and dates, like in this examples:

  1: string.Format("{0:g}", DateTime.Now); //5/08/2009 04:02 PM
  2: string.Format("{0,-9:g5}", 3.14159); // "3.1416   "

In line 1, what we said was “give me the current date and time with a general (g) format”. In line 2, it was something like “give me the number 3.14159, formatted to deliver 5 decimal places (which include the decimal point, so ‘g5’ will give only 4 decimal numbers), and complete result, aligned to the right, with spaces to reach 9 characters”.

Is the above examples, the ‘g’ character is called a Formatting Specifier. with a number to the right of a formatting specifier, we specify the number of decimal places. Here are all the others:

Numeric formatting specifiers
  1: int x = 12345;
  2: string.Format("{0:g}", x); // 12345 (general)
  3: string.Format("{0:c}", x); // $12,345 (currency)
  4: string.Format("{0:e}", x); // 1.234500e+004 (scientific notation)
  5: string.Format("{0:f}", x); // 12345.00 (fixed-point)
  6: string.Format("{0:p}", x); // 12,345% (percent)
  7: string.Format("{0:r}", x); // 12345 (rounded)
  8: string.Format("{0:n}", x); // 12,345.00 (number with commas)
  9: string.Format("{0:d}", x); // 12345 (decimal)
 10: string.Format("{0:x}", x); // 3039 (hexadecimal)
Date and time formatting specifiers
  1: string a = DateTime.Now;
  2: string.Format("{0:d}", a); // 8/5/2009 (short date)
  3: string.Format("{0:D}", a); // Wednesday, 5 August 2009 (long date)
  4: string.Format("{0:f}", a); // Wednesday, 5 August 2009 04:35 PM (full short)
  5: string.Format("{0:F}", a); // Wednesday, 5 August 2009 04:35:17 PM (full long)
  6: string.Format("{0:g}", a); // 5/08/2009 04:35 PM (general)
  7: string.Format("{0:G}", a); // 5/08/2009 04:35:17 PM (general long)
  8: string.Format("{0:m}", a); // 5 August (month day)
  9: string.Format("{0:o}", a); // 2009-08-05T16:35:17.4687500-05:00 (round trip)
 10: string.Format("{0:R}", a); // Wed, 5 August 2009 16:35:17 GMT (RFC1123 pattern)
 11: string.Format("{0:s}", a); // 2009-08-5T16:35:17 (sortable)
 12: string.Format("{0:t}", a); // 04:35 PM (short time)
 13: string.Format("{0:T}", a); // 04:35:17 PM (long time)
 14: string.Format("{0:u}", a); // 2009-08-5 16:35:17Z (universal)
 15: string.Format("{0:U}", a); // Wednesday, 5 August 2009 4:35 PM (Universal GMT)
 16: string.Format("{0:Y}", a); // August 2009 (Year month)

Besides, you can always use custom formats for both numbers and dates:

  1: //Numbers
  2: "{0:0.0}" // 1234.6 (decimal point)
  3: "{0:0,0}" // 1,235 (thousands)
  4: "{0:0,.}" // 1 (number scaling)
  5: "{0:0%}" // 123456% (percent)
  6: "{0:00e+0}" // 12e+2 (scientific notation)
  7: //Dates an times
  8: "{0:MMM}" // Aug (month abbr)
  9: "{0:MMMM}" // August (month full)
 10: "{0:ss}" // 40 (seconds)
 11: "{0:tt}" // PM (am/pm)
 12: "{0:yy}" // 09 (year)
 13: "{0:yyyy}" // 2009 (year full)

A complete document about custom formats can de found here.

The final thing I want to talk about in the String.Format method is the conditional formatting. Let’s see:

  1: int x = 1;
  2: string.Format("{0:positive;negative;zero}", x);

The output of the String.Format depends on the value of the variable x. If the value is > 0, the output will be the word “positive”, which takes the first position after the “0:”. Obviously, if it’s < 0, it will display the word “negative”, and if it’s == 0, then it’ll show “zero”. Another example is:

  1: string.Format("{0:$#,##0.00;($#,##0.00);-}", x);

In this case, we’re not only formatting the number as a currency value, but also using parenthesis for negative values and a dash for zeroes.

So, getting to really know the String class, and in this particular case the String.Format method, is something that will open up a world of possibilities. Remember, most of the times the simplest things are the most important ones.

2009-07-31

Swap two variable values

That’s the typical example when we’re all learning how to code, swap the values of a and b. Well, here’s what they probably taught us:

  1: int a = 4;
  2: int b = 3;
  3: int temp;
  4: //Swap
  5: temp = a;
  6: a = b;
  7: b = temp;

And here’s the way to do it with out using the temporary variable, with just boolean logic, and the ever underestimated XOR (^):

  1: int a = 4;
  2: int b = 3;
  3: //Swap
  4: a = a ^ b;
  5: b = a ^ b;
  6: a = a ^ b;

Another way, with just pluses and minuses…

  1: int a = 4;
  2: int b = 3;
  3: a -= b;
  4: b += a;
  5: a = b - a;

I’ve actually seen many ways to do it, specially on this thread

2009-07-30

Difference between logical operators in C#

Yes, you’ve probably seen that the AND and OR logical operators have two ways of being written in C#: The first way is like this: && (AND), || (OR), and the second is this: & (AND), | (OR). In case you didn’t notice the difference, the first ones use a double operator, while the last ones use only one.

As you already might know, AND operator returns true if both sides of an expression are true, and OR operator returns true if at least one side of the expression is true.

Even though most of us programmers actually know that there are two “ways” to write the AND and OR operators, few know (that was my case before I looked it up) the difference between both. Well, here it is:

When you use double logical operators (which is probably most of the time), the compiler only evaluates the right part of the expression if the first one doesn’t already make the expression false. The opposite happens when you use single logical operators: both sides of the expression get evaluated no matter what. Let’s clear that out with an example:

  1: if(myDataSet.Tables.Count > 0 && myDataSet.Tables[0].Rows.Count > 0)
  2: {
  3:    //Do something
  4: }

Because we’re using the double AND operator (&&), the compiler will automatically mark the whole expression as false if it finds that the left side of it is already false, without even bothering to evaluate the right side. This is very useful in this specific case with the DataSet, because sometimes we need to evaluate both that the DataSet has a table, and that table has at least one row. That will save us having to use two nested if statements:

  1: if(myDataSet.Tables.Count > 0)
  2: {
  3:    if(myDataSet.Tables[0].Rows.Count > 0)
  4:    {
  5:       //Do something
  6:    }
  7: }

Now, if we use only the single AND operator, the compiler will evaluate both sides of the expression no matter what, so this code:

  1: if(myDataSet.Tables.Count > 0 & myDataSet.Tables[0].Rows.Count > 0)
  2: {
  3:    //Do something
  4: }

will result in an ArgumentNullException if our DataSet doesn’t have a table, caused by the myDataSet.Tables[0].Rows.Count > 0 comparison.

There’s one more logical operator, the XOR (^), which will return true only if both sides of the expression are different (one is true and the other is false). This, in practical terms, is the same as the DIFFERENT (!=) operator, and it doesn’t have a “double” counterpart, because obviously in this case, both sides of the expression have to always be evaluated.

How could you NOT blog?

Blogs are everywhere, and it’s so easy to create one that it’s impossible, specially if you’re in the programming world, not to get influenced by the hype. I actually did that a few years ago, but this is probably the first time I really want to make a serious blog, which might be helpful to people.

All my previous blogs were written in Spanish (I’m form Colombia, South America), but i think that a a blog in English could get to more people. Besides, this is a blog about programming (yet another one, I know, but what can you do?), and most people, even non-English speakers, would search the Web in English when it comes to those topics.

Anyway, I still have my Spanish programming blog, Puro Punto Net, and I’m sure planning on not quitting on it.

Hope you people find this blog interesting, and any comments or critiques are well appreciated.