7

I have the following C# code -

using System; class Program { static void Main() { int number = 1; int isNumber10; (number==10)?(isNumber10=1):(isNumber10=0); Console.WriteLine(isNumber10); } } 

On compilation it gives me the error -

error CS0201: Only assignment, call, increment, decrement, and new object expressions can be used as a statement

In C I am used to the following code -

#include <stdio.h> int main(){ int isNumber10; int number = 1; (number==10)?(isNumber10=1):(isNumber10=0); printf("%d\n",isNumber10); return 0; } 

And this code is running perfectly.

Now, the two programs are exactly same. So why is it running in C but not in C#?

2
  • 3
    Because C# is not C, not even close in most cases. Commented Dec 21, 2017 at 1:32
  • 2
    Ill make the post look pretty instead Commented Dec 21, 2017 at 1:33

3 Answers 3

15

The ternary operator is an expression that cannot be used as a statement. In contrast, an assignment is an expression that can be promoted to a statement. (hence the error message referring to "assignment" expressions)

What you want is:

isNumber10 = number == 10 ? 1 : 0; 

Here you are using the ?: operator as an expression that resolves to one of the two values (1 or 0) and is then assigned to the variable isNumber10.

To have a little fun with this, if you created this method:

public void M<T>(T value) { } 

And you called it like:

M((number==10)?(isNumber10=1):(isNumber10=0)); 

It would work fine. The problem is just that the C# grammar does not allow most naked expressions to live in a context in which the value of the expression is not consumed. (Remember, the defining difference between an expression and a statement is that an expression produces an expression, but a statement does not) Some expressions are allowed outside of this guidance -- for example invoking a method that returns a value. These become in the technical parlance an "expression statement". And usefully, the only candidates for expressions that can be promoted to statements are exactly delineated by the error message in your question's title.

Most of us think of assignments as statements, but it is more fundamentally an expression. (it returns the value assigned while simultaneously performing the assignment). That's why that empty call to M will actually accomplish what you want. (not that it's very readable)

From your comment, I'll add this comment as part of my answer:

The only error of yours is the simple fact that the C# grammar doesn't allow it. It certainly could, but well, it does not. I'm reminded about how the when operator in SQL is an expression (meaning you can say set i = when x is null then 'A' else 'B') whereas in C# such a usage would be invalid (since the switch statement is not an expression -- it cannot return a value)

Sign up to request clarification or add additional context in comments.

6 Comments

But in my code I am checking condition - (number==10)? if true the statement is (isNumber10=1), if false the statement is (isNumber10=0), where is wrong in this approach?
@puregeek Maybe go read the docs, probably would have been a better place to start.
@DavidG I read it, but please explain to me, where is grammatical error in my approach? First I check condition, if true I do something, if false I do something
@puregeek the only error of yours is the simple fact that the C# grammar doesn't allow it. It certainly could, but well, it does not. I'm reminded about how the when operator in SQL is an expression (meaning you can say set i = when x is null then 'A' else 'B') whereas in C# such a usage would be invalid (since the switch statement is not an expression -- it cannot return a value)
@KirkWoll Please make this comment as answer because none of the answers are satisfactory
|
2

try this:

int number = 1; int isNumber10 = (number == 10) ? 10 : 0; Console.WriteLine(isNumber10); 

7 Comments

I know this method, but both approach should be correct, why mine one is not correct?
it is because you put a closing tag of this int isNumber10; Instead of ; it must be =;
It must be look like this int isNumber10=(number == 10) ? (isNumber10 = 1) : (isNumber10 = 0); but it is not a good habit in programming because it is allocate space . the right way is int isNumber10 = number == 10 ? 10 : 0;
OK, but in my statement why after evaluating condition, true and false part are not getting executed?
it is executed try to add Console.ReadLine(); at the end.
|
0

The problem is that C grammar and C# grammar are different.

I am giving a simple example -

There is a man John

In C the following statement is valid -

(John has beard)?(Ask John to save):(ask John to not save); 

Here John has to be referred twice.

Also the following statement is valid -

Ask John to = (John has beard)? (save):(not save); 

Here John is referred only once.

But In C# only the following statement is valid -

Ask John to = (John has beard)? (save):(not save); 

Like that in the given code -

Correct C Syntax -

(number==10)?(isNumber10=1):(isNumber10=0); 

as well as -

isNumber10 = (number==10)? 1:0; 

but in C# only the following syntax is Correct -

isNumber10 = (number==10)? 1:0; 

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.