473,399 Members | 3,302 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,399 software developers and data experts.

Tertiary Operator Confusion ( a = b ? c : d)

I don't know if this is a compiler error or not. It all kind of makes sense
but you would think that the compiler would check the types of the possible
outcomes of the tertiary operator (c and d) against the type of the variable
being assigned (a). Instead it compares the types of c and d which may not
be compatible. Just seems silly.

int? i;
object o;

//this is ok:
if (i.HasValue)
o = i;
else
o = DBNull.Value;

//this fails to compile
//Error 1 Type of conditional expression cannot be determined because
//there is no implicit conversion between 'int?' and 'System.DBNull'

o = i.HasValue ? i : DBNull.Value;

//these also fail for the same reason

o = i == null ? DBNull.Value: i;
o = i.HasValue ? i : "ABC";

//but these works

o = i.HasValue ? (object)i : DBNull.Value;
o = i.HasValue ? (object)i : (object)DBNull.Value;
o = i.HasValue ? i : (object)DBNull.Value;

Jan 26 '07 #1
10 13895
One observation. It does seem that the compiler is enforcing the rule
that both alternatives must have the same type. This makes sense to me
when you consider that such tertiary expressions can be used in
complicated compound expressions where the ultimate target type is not
as obvious as it might be with a simple assignment statement.

==============
Clay Burch
Syncfusion, Inc.

Jan 26 '07 #2

"ClayB" <cl***@syncfusion.comwrote in message
news:11**********************@s48g2000cws.googlegr oups.com...
One observation. It does seem that the compiler is enforcing the rule
that both alternatives must have the same type. This makes sense to me
when you consider that such tertiary expressions can be used in
complicated compound expressions where the ultimate target type is not
as obvious as it might be with a simple assignment statement.
However all expressions in .NET have a common type, which is object.
Probably the current error should be replaced with a warning, with the
ternary expression resolved as the nearest common supertype which may be
object, or the union of object with some set of interfaces. The compiler
could then determine which interface is subsequently used and automatically
generate the cast.
>
==============
Clay Burch
Syncfusion, Inc.

Jan 26 '07 #3
On Jan 26, 2:07 pm, "Ben Voigt" <r...@nospam.nospamwrote:
One observation. It does seem that the compiler is enforcing the rule
that both alternatives must have the same type. This makes sense to me
when you consider that such tertiary expressions can be used in
complicated compound expressions where the ultimate target type is not
as obvious as it might be with a simple assignment statement.
However all expressions in .NET have a common type, which is object.
Probably the current error should be replaced with a warning, with the
ternary expression resolved as the nearest common supertype which may be
object, or the union of object with some set of interfaces. The compiler
could then determine which interface is subsequently used and automatically
generate the cast.
Here are the rules which are actually used. Personally, I think it's
fine as it is:

<quote>
The second and third operands of the ?: operator control the type of
the conditional expression. Let X and Y be the types of the second and
third operands. Then,

*If X and Y are the same type, then this is the type of the
conditional expression.
*Otherwise, if an implicit conversion (§13.1) exists from X to Y,
but not from Y to X, then Y is the type of the conditional expression.
*Otherwise, if an implicit conversion (§13.1) exists from Y to X,
but not from X to Y, then X is the type of the conditional expression.
*Otherwise, no expression type can be determined, and a
compile-time error occurs.
</quote>

Jon

Jan 26 '07 #4
C# specification 2.0, 24.2.3:
... The compiler could then determine which interface is subsequently used
and automatically generate the cast.
"However, a nullable type never satisfies an interface constraint, even if
the underlying type implements the particular interface"
"Ben Voigt" <rb*@nospam.nospamha scritto nel messaggio
news:u2**************@TK2MSFTNGP04.phx.gbl...
>
"ClayB" <cl***@syncfusion.comwrote in message
news:11**********************@s48g2000cws.googlegr oups.com...
>One observation. It does seem that the compiler is enforcing the rule
that both alternatives must have the same type. This makes sense to me
when you consider that such tertiary expressions can be used in
complicated compound expressions where the ultimate target type is not
as obvious as it might be with a simple assignment statement.

However all expressions in .NET have a common type, which is object.
Probably the current error should be replaced with a warning, with the
ternary expression resolved as the nearest common supertype which may be
object, or the union of object with some set of interfaces. The compiler
could then determine which interface is subsequently used and
automatically generate the cast.
>>
==============
Clay Burch
Syncfusion, Inc.


Jan 26 '07 #5
"Andrew Robinson" <ne****@nospam.nospamschrieb im Newsbeitrag
news:uo**************@TK2MSFTNGP03.phx.gbl...
>I don't know if this is a compiler error or not. It all kind of makes sense
but you would think that the compiler would check the types of the possible
outcomes of the tertiary operator (c and d) against the type of the
variable being assigned (a). Instead it compares the types of c and d which
may not be compatible. Just seems silly.

int? i;
object o;

//this is ok:
if (i.HasValue)
o = i;
else
o = DBNull.Value;

//this fails to compile
//Error 1 Type of conditional expression cannot be determined because
//there is no implicit conversion between 'int?' and 'System.DBNull'

o = i.HasValue ? i : DBNull.Value;

//these also fail for the same reason

o = i == null ? DBNull.Value: i;
o = i.HasValue ? i : "ABC";

//but these works

o = i.HasValue ? (object)i : DBNull.Value;
o = i.HasValue ? (object)i : (object)DBNull.Value;
o = i.HasValue ? i : (object)DBNull.Value;

BTW

you also could use the null coalescing operator:

o = i ?? (object)DBNull.Value

But still you have to cast to object.

Christof
Jan 26 '07 #6
Onather remark:

if you cast the i to object, the result will be a boxed nullable int, not a
boxed int.
Could be an important difference.

"Andrew Robinson" <ne****@nospam.nospamschrieb im Newsbeitrag
news:uo**************@TK2MSFTNGP03.phx.gbl...
>I don't know if this is a compiler error or not. It all kind of makes sense
but you would think that the compiler would check the types of the possible
outcomes of the tertiary operator (c and d) against the type of the
variable being assigned (a). Instead it compares the types of c and d which
may not be compatible. Just seems silly.

int? i;
object o;

//this is ok:
if (i.HasValue)
o = i;
else
o = DBNull.Value;

//this fails to compile
//Error 1 Type of conditional expression cannot be determined because
//there is no implicit conversion between 'int?' and 'System.DBNull'

o = i.HasValue ? i : DBNull.Value;

//these also fail for the same reason

o = i == null ? DBNull.Value: i;
o = i.HasValue ? i : "ABC";

//but these works

o = i.HasValue ? (object)i : DBNull.Value;
o = i.HasValue ? (object)i : (object)DBNull.Value;
o = i.HasValue ? i : (object)DBNull.Value;

Jan 26 '07 #7
Christof Nordiek wrote:
you also could use the null coalescing operator:

o = i ?? (object)DBNull.Value
Hmm, that's interesting... I've not seen that used before. Printed and
stuck on my note board :)

--
Dylan Parry
http://electricfreedom.org | http://webpageworkshop.co.uk

Programming, n: A pastime similar to banging one's head
against a wall, but with fewer opportunities for reward.
Jan 26 '07 #8
It's actually a ternary operator, not a tertiary operator. Ternary refers to
the number of arguments. Tertiary would imply a ranking (primary, secondary,
tertiary).

///ark
Jan 26 '07 #9
Mark Wilden <mw*****@communitymtm.comwrote:
It's actually a ternary operator, not a tertiary operator. Ternary refers to
the number of arguments. Tertiary would imply a ranking (primary, secondary,
tertiary).
It's *a* ternary operator, and it's better described as *the*
conditonal operator. It happens to be the only ternary operator at the
moment (IIRC) but it's not guaranteed to be an unambiguous description
forever :)

--
Jon Skeet - <sk***@pobox.com>
http://www.pobox.com/~skeet Blog: http://www.msmvps.com/jon.skeet
If replying to the group, please do not mail me too
Jan 26 '07 #10
"Jon Skeet [C# MVP]" <sk***@pobox.comwrote in message
news:MP************************@msnews.microsoft.c om...
Mark Wilden <mw*****@communitymtm.comwrote:
>It's actually a ternary operator, not a tertiary operator. Ternary refers
to
the number of arguments. Tertiary would imply a ranking (primary,
secondary,
tertiary).

It's *a* ternary operator
Isn't that what I said? :)
>, and it's better described as *the* conditonal operator
Agreed.

///ark
Jan 29 '07 #11

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

5
by: Vijai Kalyan | last post by:
Hello, I have come back to C++ after a couple of years with Java so I am quite rusty and this question may seem poor: My platform is Windows XP with MSVC 7.1. I have a class with a...
2
by: Taran | last post by:
Hi All, I was trying some code which essentially does what the function 'func' here does. To simplify the things and make a consise post I have created a dummy app to show my problem. The issue...
10
by: abcd | last post by:
x = None result = (x is None and "" or str(x)) print result, type(result) --------------- OUTPUT --------------- None <type 'str'>
16
by: Norman Diamond | last post by:
In an antique obsolete version of MFC, a CString expression could be subscripted in order to retrieve one element. Visual Studio 2005 defines CSimpleStringT::operator. At first glance it looks...
11
by: jakester | last post by:
I am using Visual C++ 2007 to build the code below. I keep getting linkage error. Could someone please tell me what I am doing wrong? The code works until I start using namespace for my objects. ...
8
by: Tyno Gendo | last post by:
I have just written a line of code like this (yes, many people think this stinks bad): <?php true == isset($page_seq) ? echo "$page_seq" : false; ?> However it breaks with 'Unexpected T_ECHO'...
22
by: clicwar | last post by:
A simple program with operator overloading and copy constructor: #include <iostream> #include <string> using namespace std; class Vector { private: float x,y; public: Vector(float u, float...
17
by: Corey Cooper | last post by:
I have a class for which I needed to create an operator= function. I then use that as a base class for another class, which also needs an operator=. What is the syntax to use in the derived class...
14
by: KK | last post by:
Dear All I have a small problem with using as operator on value type array. Here is an example what I am trying to do. using System; using System.Collections.Generic; using System.Text;
0
by: Charles Arthur | last post by:
How do i turn on java script on a villaon, callus and itel keypad mobile phone
0
by: emmanuelkatto | last post by:
Hi All, I am Emmanuel katto from Uganda. I want to ask what challenges you've faced while migrating a website to cloud. Please let me know. Thanks! Emmanuel
0
BarryA
by: BarryA | last post by:
What are the essential steps and strategies outlined in the Data Structures and Algorithms (DSA) roadmap for aspiring data scientists? How can individuals effectively utilize this roadmap to progress...
0
by: Hystou | last post by:
There are some requirements for setting up RAID: 1. The motherboard and BIOS support RAID configuration. 2. The motherboard has 2 or more available SATA protocol SSD/HDD slots (including MSATA, M.2...
0
marktang
by: marktang | last post by:
ONU (Optical Network Unit) is one of the key components for providing high-speed Internet services. Its primary function is to act as an endpoint device located at the user's premises. However,...
0
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...
0
by: Hystou | last post by:
Overview: Windows 11 and 10 have less user interface control over operating system update behaviour than previous versions of Windows. In Windows 11 and 10, there is no way to turn off the Windows...
0
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing,...
0
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome a new...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.