I am new to learning C and I would like to know if it is possible to launch more than 1 instruction inside ternary oparator in C - for example:
int a = 5;
int b = 7;
int max;
int min;
max = (a>b) ? a, b = min : b, a = min;
pritnf("%d %d", min, max);
I want to sort those numbers and assign them to a variable max or min. Is it possible to tell the program that if a > b it will save a as maximum and assign b to minimum? Or do I have to do it using If function? I think the problem is in using the comma, but I dont know what should I use instead. The message I get is this:
warning: left operand of comma operator has no effect [-Wunused-value] int max = (a>b) ? (a, b = min) : (b, a = min);
CodePudding user response:
You've got your assignment (=
) and the comma operator (,
) backward.
But as suggested in the comments this is obscure and unnecessarily difficult to read.
Just write an if
statement:
int a = 5;
int b = 7;
int max;
int min;
if(a>b){
max=a;
min=b;
}else{
max=b;
min=a;
}
It isn't bad practice to use the ternary operator but avoid using it to perform multiple actions like this. Don't treat it as some kind of inline alternative to if
just because you can.
The advice for the comma operator (,
) is more generally to avoid it.
It's superfluous, error-prone and can be confused with the comma delimiter in function calls and declarations.
CodePudding user response:
The conditional operator in C is defined the following way
conditional-expression:
logical-OR-expression
logical-OR-expression ? expression : conditional-expression
The assignment and the comma operator have lower precedence.
So this statement
max = (a>b) ? a, b = min : b, a = min;
is equivalent to the following statement
max = ( (a>b) ? a, b = min : b) , a = min;
Thus the variables max
and b
are set to the indeterminate value of the variable min
if a
is greater than b
or to the value of the variable b
otherwise. And then the variable a
in turn is set to the indeterminate value of min
.
It seems what you are trying to achieve is the following
max = a > b ? min = b, a : ( min = a, b );
Though the code will be more readable if to split this statement into two statements like
max = a > b ? a : b;
min = a > b ? b : a;
Pay attention to that there is a difference between the definition of the compound operator in C and C . In C the compound operator is defined like
conditional-expression:
logical-or-expression
logical-or-expression ? expression : assignment-expression
that is the third operand can be an assignment expression.
For example in C you may write
a < b ? max = b : max = a;
while in C this statement will look like
( a < b ? max = b : max ) = a;
and the compiler will issue an error message because the left operand of the assignment is rvalue
instead of lvalue
.
CodePudding user response:
The syntax of the conditional expression is:
conditional-expression:
logical-OR-expression
logical-OR-expression ?
expression :
conditional-expression
Therefore, you must use parentheses at least for the third operand because of operator precedence.
Furthermore, your assignments were incorrect.
Here is a modified version:
#include <stdio.h>
int main() {
int a = 5;
int b = 7;
int max;
int min;
max = a > b ? min = b, a : (min = a, b);
printf("%d %d\n", min, max);
return 0;
}
Output: 5 7
To avoid compiler warnings, you could write:
max = a > b ? ((void)(min = b), a) : ((void)(min = a), b);
Note however that this method is very unusual, confusing and error prone. Use the ternary operator to perform just one computation at a time:
int max = (a > b) ? a : b; // max could even be declared as const int max = ...
int min = (a > b) ? b : a; // same for min
or just use an if
statement:
if (a > b) {
max = a;
min = b;
} else {
max = b;
min = a;
}
C is very versatile... Not every possibility is to be used and abused. Here are some more convoluted ones to avoid:
// recursive
*(a > (*(a > b ? &min : &max) = b) ? &max : &min) = a;
// symmetric
(min = a) < (max = b) || (max = a) > (min = b);
// compact
(min = max = a) > b ? (min = b) : (max = b);
CodePudding user response:
Does this not work?
(a < b) ? {min = a; max = b;} : {min = b; max = a;}
It's not beautiful, but usually you can use an execution scope as an expression argument, works for switch-case, I see no reason why it would not work here.
CodePudding user response:
Don't abuse the conditional operator. Doing so only makes code cryptic.
Instead, you can use C's innate values of 1 (true) and 0 (false.)
This code looks a bit more complex because it has 3 test cases. Apart from the tiny array pair
, it is directly translatable to your simpler code.
int main() {
int test[][2] = { { 5, 7 }, { 5, 5 }, { 5, 3 }, };
for( int i = 0; i < sizeof test/sizeof test[0]; i ) {
// two assignments, just like "int a = 5; int b = 7;"
int pair[2] = { test[i][0], test[i][1] };
// a conditional (stored for use)
int max = ( pair[0] < pair[1] );
// a print statement
printf( "%d %d\n", pair[!max], pair[max] );
}
return 0;
}
5 7
5 5
3 5
Think about reading your code in 6 months or 6 years. "What was I thinking???"