Chaining the C# ?? Operator
C# 2.0 has a nice ?? operator that works as a shortcut for:
string value1 = null;
string value2 = "Test1";
string result = value1 != null ? value1 : value2;
which causes result containing Test1 or the second value.
In C# you can shortcut this special null comparison case with the new ??:
string result = value1 ?? value2;which is a little easier to write. This is probably not news to you, but what's really useful is that you can chain these operators together so you can do a whole bunch of null comparisons in a single stroke. For example, I frequently look for a few different querystring variables in a page:
string partner = Request.QueryString["GoogleId"] ??
Request.QueryString["PartnerId"] ??
Request.QueryString["UserKey"] ??
string.Empty;
which still yields a valid result for the first non-null querystring or if nothing is found returning "".
Note that this also works with the longhand syntax in the first example if you use brackets, but more than one level gets pretty unreadable quickly. The ?? syntax on the other is easily readable. This can certainly save you from writing a bunch of nested IF statements to check for multiple conditions.
Reminds me a bit of JavaScript code using || syntax for null checking, and maybe that's why I just ran into the chaining aspect now <g>...
The Voices of Reason
# re: Chaining the C# ?? Operator
In practice though, a Request.QueryString["key"] should be checked using a method like IsNullOrEmpty:
bool IsNullOrEmpty(string s)
{
if (s == null || s == string.Empty || s.Trim() == string.Empty)
return false;
return true;
}
Cool example.
# re: Chaining the C# ?? Operator
Why write your own IsNullOrEmpty when string.IsNullOrEmpty exists? Granted, it doesn't automatically trim the string but string.IsNullOrEmpty(s.Trim()); would get you the same result.
Rick,
Nice method. I've been trying to use similar techniques to make my validation routines more readable. I'd kill for a &&= operator so that this:
bool isValid = true; isValid = isValid && (obj != null); isValid = isValid && (obj.IsLoaded);
Could become:
bool isValid = true; isValid &&= (obj != null); isValid &&= (obj.IsLoaded);
That way once isValid went false the second half of the expression wouldn't be evaluated. &= exists but its not short-circuited like &&.
# re: Chaining the C# ?? Operator
# re: Chaining the C# ?? Operator
# re: Chaining the C# ?? Operator
# re: Chaining the C# ?? Operator
And btw, (s.Length == 0) is far more faster than (s == string.Empty) and it is how IsNullOrEmpty was coded by MS.
# re: Chaining the C# ?? Operator
>> Granted, it doesn't automatically trim the string but
>> string.IsNullOrEmpty(s.Trim()); would get you the same result.
No.
If you did something like:
string s = null;
bool b = string.IsNullOrEmpty(s.Trim());
You'd get argument null exception (because s *is* null).
In the above post short-circuit (e.g. || and not |) operator is used, so first thing that gets checked is null reference and everything is OK.
Personally, I like to declare extension method:
public static bool IsEmpty(this string s)
{
return s == null || s.Length == 0 || s.Trim().Length == 0;
}
This way, example works OK.
string s = null;
bool b = s.IsEmpty();
LP,
Dejan
# re: Chaining the C# ?? Operator
Most people would consider a padded string not empty because if you have one most likely there's a reason for it.
# re: Chaining the C# ?? Operator
Rick,
I actually use the "question mark" questions when we are interviewing sr. developers at my job. Ternary operator (?), null coalescing (??) and nullable types (int?). It gives a nice theme to the interview. But to add to you post, the ternary operator and null coalescing are pretty powerful..because of the brevity they provide when chaining multiple "if type" statements.
# re: Chaining the C# ?? Operator
https://connect.microsoft.com/VisualStudio/feedback/ViewFeedback.aspx?FeedbackID=306293
This would make it possible to change this:
string currentValue = String.Empty;
if (AppSettings != null && AppSettings[Key] != null)
{
currentValue = AppSettings[Key].Value ?? String.Empty;
}
to
string currentValue = AppSettings?.GetElementKey(Key)?.Value ?? String.Empty;
Yours,
Alois Kraus
# re: Chaining the C# ?? Operator
There are methods like string.IsNullOrEmpty but furthermore you show off some IDs that need to be parsed.
So i usually prefer to parse them through int.TryParse
int result; if (!int.TryParse(Request.QueryString["SomeId"], Result)) { throw new Exception("Not parseable"); }
But I agree, the ?? operator is quite powerful indeed, you just didn't pick the right example.
greetings Daniel
# re: Chaining the C# ?? Operator
# re: Chaining the C# ?? Operator
Fixed in 2.0 SP1 (and 3.5): http://support.microsoft.com/kb/945757
# re: Chaining the C# ?? Operator
public void InsertStringIntoDataRow(string element, DataRow row)
{
row["something"] = element ?? DBNull.value;
}
you get a compilation error because of the difference in types....A shame :(
# re: Chaining the C# ?? Operator
public void InsertStringIntoDataRow(string element, DataRow row) { row["something"] = element ?? DBNull.value; }
I'f i'm not mistaken, all you have to do is cast one or both of the arguments to object. This should work since your are using an untyped DataRow object. This should except arguments of type object. I've done this before when using the ternary ?: operator to add SqlParameters to a SqlParameterCollection, as follows:
SqlParameterCollection params = new SqlParameterCollection (); params.AddWithValue("@ParentNamespaceID", nmRow.IsParentNamespace_IDNull() ? DBNull.Value : (object)nmRow.ParentNamespace_ID);
# re: Chaining the C# ?? Operator
public static class Validator
{
public static T IsNull<T>(object value, T defaultValue)
{
return ((Object.Equals(value, null)) | (object.Equals(value, DBNull.Value)) ? (T)defaultValue : (T)value);
}
public static T IsNull<T>(object value)
{
return IsNull<T>(value, default(T));
}
}
# re: Chaining the C# ?? Operator
x &= y;
is equivalent to
x = x & y;
except that x is only evaluated once. The & operator performs a bitwise logical AND operation on integral operands and logical AND on bool operands.
# re: Chaining the C# ?? Operator
Which do you think looks better? (And is more OO)
String.IsNullOrEmpty(myString)
or
myString.IsEmpty()
In a way, this has better functionality as an extension than if it were implemented directly on the String class, because obviously you can't call an instance method if the instance is null :)
I still think PHP / Javascript have it better...
if ($myString) {
// string isn't empty!
}
I wonder if an implicit cast to bool would be possible on a string?
# re: Chaining the C# ?? Operator
/// <summary>
/// Tests whether a tring is null or empty, and if so returns the
/// alternate instead of the source value.
/// </summary>
/// <param name="str">The source string</param>
/// <param name="alternateValue">The alternate value</param>
/// <returns>A string</returns>
public static string IfNullOrEmpty(this string str, string alternateValue)
{
if (str == null || str.Length == 0 || str.Trim().Length == 0)
{
return alternateValue;
}
return str;
}
Example Usage:
string someVar = Request.QueryString["someID"].IfNullOrEmpty("SomeDefaultValue");
# re: Chaining the C# ?? Operator
IsNullOrWhiteSpace is a convenience method that is similar to the following code, except that it offers superior performance:
return String.IsNullOrEmpty(value) || value.Trim().Length == 0;
http://msdn.microsoft.com/en-us/library/system.string.isnullorwhitespace.aspx
:)
# re: Chaining the C# ?? Operator
Cool, I like this. Now, how can I do it in VB?!
change to c# vb.net was never supposed to be released
# re: Chaining the C# ?? Operator
s + "" != ""
nice way to do it.