views:

94

answers:

2

I have the below linq query which takes a text field which may be Y, N or DBnull and populates a boolean? parameter with either True, False or null depending on the value of the field.

            var dset = from i in tbdc.Talkbacks
                   where i.talkback_id == id
                   select new Talkback(i.talkback_id, i.acad_period, i.reference,
                                       i.staff_member, i.date_received, i.no_talkers,
                                       i.gender_id, i.names, i.type_id,
                                       i.method_id, i.area_id, i.site_id,
                                       i.category_id, i.date_closed, i.expenddate,
                                       i.acknowledgementtarget,
                                       (i.targetmet == "Y") ? true : ((i.targetmet == "N") ? false : null),
                                       (i.acknowledgementtargetmet != "N") ? true : false

The problematic line is

(i.targetmet == "Y") ? true : ((i.targetmet == "N") ? false : null)

After reading up I found some documentation which states that the 2nd and 3rd arguments of the inline if need to be of the same type or be implicitly convertible to one another.

My question is, how do I get around this limitation to achieve my desired result?

I am relatively new to C# so am not familiar with all its quirks/capabilities yet.

+2  A: 

You can explicitly convert one or more of the expressions to a bool?:

(i.targetmet == "Y") ? true : ((i.targetmet == "N") ? (bool?)false : (bool?)null)
Quartermeister
+3  A: 

My suggestion would be to replace it with :

(i.targetmet != null) ? (bool?)(i.targetmet == "Y") : null;

the reason why the compiler does not agree without the cast is that even if you store it into a nullable structure, the ternary operation checks if the results are compatible through an implicit conversion.

Results true and false are treated as bool literals, not bool?, thus not implicitly convertible to null. Casting either results to bool? will make them comparable. The one I suggested has an implicit convertion between bool? and null, and this works too:

(i.targetmet != null) ? (i.targetmet == "Y") : (bool?)null;

Which is an implicit conversion between a bool and bool?. I arbitrary prefer the first one..

Dynami Le Savard
That worked great Dynami. I am now getting a problem further down the line where I am trying to use the value in a DisplayTemplate with the below code:<%@ Control Language="C#" Inherits="System.Web.Mvc.ViewUserControl<System.Boolean?>" %><%: ((Boolean?)Model.Value == True) ? "kpi_tick.png" : "kpi_cross.png" %>The idea is that it will display a tick image for true, cross image for false, and no image for undefined (haven't done that bit of the code yet). I am getting the error "The name 'True' does not exist in the current context"
hermiod
This markup looks like ASP.NET, which I having worked with much lately. So random shot in the dark : replace True with true ?
Dynami Le Savard
Create a static class called BoolHelper with a static method bool Parse(string s) that contains Dynami's solution. Then use that to simplify things for your parser.
Peter Wone