Warning: second/third operand of conditional has no effect [-Wunused-value] - c++

std::cout << (abs(b - c) < a) && a < b + c ? 1 : 0;
I want to check if given values can create triangle. I got warnings:
second operand of conditional expression has no effect [-Wunused-value]
third operand of conditional expression has no effect [-Wunused-value]
What's wrong?

Your code translates to:
((std::cout << (abs(b - c) < a)) && a < b + c) ? 1 : 0;
Firstly, operator<< has higher operator precedence than operator&&.
Only the value of abs(b - c) < a will be printed and the (a < b + c ? 1 : 0) part will be AND-ed together with the return value of std::ostream::operator bool.
But the warning is about 1 and 0 not being assigned to anything nor having any side effects, because && precedes the ternary conditional (?:).
The correct code is either:
std::cout << (abs(b - c) < a && a < b + c ? 1 : 0);
// same as std::cout << ((abs(b - c) < a && a < b + c) ? 1 : 0);
or
std::cout << (abs(b - c) < a && (a < b + c ? 1 : 0));
In fact, they're equivalent (apart that one calls operator<< with bool and the other with int), no ternary operator needed:
std::cout << (abs(b - c) < a && a < b + c);

Related

IF-nesting in c++

heyall, just going through some textbook examples for my introductory c++ course and I would really appreciate it if somebody could clarify why the following code produces an output of 51 (I would expect it to not produce any output whatsoever), many thanks!:
#include <iostream>
using namespace std;
int main()
{
constexpr int a{9};
constexpr int b{1};
constexpr int c{5};
if (a < b < c)
if (c > b > a)
if (a > c) cout << 91;
else cout << 19;
else
if (b < c) cout << 51;
else cout << 15;
else
if (b < a < c)
if (a < c) cout << 95;
else cout << 59;
else
if (b < c) cout << 57;
else cout << 75;
return 0;
}
It seems you expect this expression:
if (a < b < c)
to be true if a, b, and c are in increasing order. But what actually happens is the expression becomes:
if ((a < b) < c)
which is either:
if (0 < c)
// or
if (1 < c)
Either way, that's probably not what you want. In fact, there's no good reason to ever write the above expression.
If you want to check whether the variables are increasing, you need to write something like:
if (a < b && b < c)
In c++, comparisons like 'X<=Y<=Z' do not have their mathematical meaning without parentheses. So, in
if (a < b < c)
we are getting
a < b => 9 < 1 => 0
'0' means the condition is false, which with 'c' is returning
0 < 5 => 1
"1" being returned means that the if condition is True.
Similarly, you can check for the nested if-else loops.

How does c++ evaluate assignment operators (if statement)

Consider the following
int main() {
int a = 8;
int b = 10;
while (true) {
if (a /= 2 && b < 12) {
b++;
std::cout << b << std::endl;
}
else break;
}
return 0;
}
Now c++ is not my main language, but how does c++ evaluate this if statement?
In this case, when b>=12, the compiler throws the "division by zero" exception, but why?
Now if i wrap the states in parentheses i do not get the exception.
if( (a /= 2) && (b < 12))
Does this have something to do with how c++ evaluates the statements?
If evaluation is not the problem:
I am aware of that
a = (a/2 && b<12)
would not hold either.
P Λ Q does not hold for P Λ ¬Q but the state of P should not be affected? Why is it P gets blamed instead of ¬Q?
if (a /= 2 && b < 12)
is the same as:
if (a /= (2 && b < 12))
so:
2 is evaluated, which is converted to true in the context of an operand to &&. This does not trigger short-circuit evaluation so we continue...
b < 12, which in the case you're talking about is false
So 2 && b < 12 evaluates to false overall
a /= 2 && b < 12 is therefore equivalent to a /= false here, which is equivalent to a /= 0.

What does this arithmetic expression mean: A += B++ == 0 in C++;

I came accross this expression, and can't understand the meaning of line 3 in the following snippet:
int A=0, B=0;
std::cout << A << B << "\n"; // Prints 0, 0
A += B++ == 0; // how does this exp work exactly?
std::cout << A << B << "\n"; // Prints 1, 1
A adds B to it, and B is Post incremented by 1, what does the "==0" mean?
Edit:
Here's the actual code:
int lengthOfLongestSubstringKDistinct(string s, int k) {
int ctr[256] = {}, j = -1, distinct = 0, maxlen = 0;
for (int i=0; i<s.size(); ++i) {
distinct += ctr[s[i]]++ == 0; //
while (distinct > k)
distinct -= --ctr[s[++j]] == 0;
maxlen = max(maxlen, i - j);
}
return maxlen;
}
B++ == 0
This is a boolean expression resulting in true or false. In this case the result is true, true is then added to A. The value of true is 1 so the (rough) equivalent would be:
if(B == 0)
A += 1;
++B;
Note that this isn't particulary good or clear to read code and the person who wrote this should be thrown into the Gulags.
Lets break this expression into pieces: A += value, whereas value = B++ == 0. As later cout suggests, value == 1. Why is that? Here is why: value is result of comparison of B++ and 0, but ++ (increment) operation, when written after operand, is being processed after the comparison, i.e. if you write A += ++B == 0 the later cout should (and does) print 0, 1.

Meaning of (n & 1 << b) in C++

While referring a C++ code written by someone else in CodeChef for a particular problem I found a new way(at least for me) of writing a conditional statement like this: if (n & 1 << b).
The entire code snippet(a function) is as follows:
int Solve(int tim, int n)
{
if (tim < 0)
return 1;
int res = 0;
for (int b = Maxb - 1; b >= 0; b--)
if (n & 1 << b)
{
int my = b - __builtin_popcount(tim & ((1 << b) - 1));
res += 1 << my;
if (tim & 1 << b)
return res;
}
res++;
return res;
}
I know the bitwise AND operation and also a left shift operation means when we use separately. However, here the combination of both in a conditional statement made me confuse to read the logic. When I searched for the references, I couldn't find a situation where both operations come up together. Therefore, can anybody tell me the meaning or what exactly going on here?
It's a check to see if the bit at position 'b' in the binary representation of n is turned on or off.
if (n & 1 << b)
is essentially
if (n & (1 << b))
because of operator precedence.
these are the values that 1 << b gets (righthand side is in binary):
For b == 0, (1 << b) == ...000000001
For b == 1, (1 << b) == ...000000010
For b == 2, (1 << b) == ...000000100
For b == 3, (1 << b) == ...000000100
For b == 3, (1 << b) == ...000001000
For b == 4, (1 << b) == ...000010000
and so on.
When you & the value 1 << b with n you essentially turn off all of n's bits except for the bit in the location corresponding to the 1 in the binary representation of 1 << b.
This means that you would only get a non-zero result for n & (1 << b) if the bit of n that was in the location corresponding to the 1 bit of (1 << b) was turned on. If it wasn't, all of the bits would turn off and since it was already 0, it would stay 0 and the end result would be 0.
The if statement receives this final result, if it's positive (the bit was on) it will enter the if, otherwise (if the bit was off), the end result would be 0 and the if statement would consider the statement n & (1 << b) to be false.
Per http://en.cppreference.com/w/cpp/language/operator_precedence
<< takes precedence over &. So, like #Ryan's comment, (n & 1 << b) is equivalent to (n & (1 << b))

How to do equal comparison in C or C++?

I am just wondering in C or C++, for the expression:
b == c || b == d
Can I do something like:
b == (c || d)
and get the same behavior?
The first expression
b == c || b == d will give you true if b is equal to either c or d.
The second expression
b == (c || d) will check only if b is either equal to 0 or 1 because the output of c || d is binary.
Consider this code:
#include <iostream>
using namespace std;
int main() {
int b=10,c=9,d=10;
cout << (b ==c || b ==d )<<endl;
cout<< ( b == ( c || d)) <<endl;
d=11;
cout << (b ==c || b ==d )<<endl;
cout<< ( b == ( c || d)) <<endl;
return 0;
}
The output is
1
0
0
0
Now you can clearly see that both expressions are not same.
No, operators in C and C++ don't implicitly distribute over subexpressions like that. Evaluation is defined strictly in terms of the direct association of operators with operands. There are no "shortcuts" as you might have in mathematics or English.
If you write code that incorrectly assume such implicit distribution, you're likely to end up with an expression that's syntactically and semantically valid, but that doesn't do what you expect.
The || operator yields a value of 1 or true if either operand is true (non-zero) or a value of 0 or false if both operands are false (equal to zero). And the operands needn't be boolean; they can be of any scalar type. (In C the result is of type int; in C++ it's of type bool.) The expression
b == c || b == d
is equivalent to
(b == c) || (b == d)
and yields a true result if b is equal to c or if b is equal to d. But this expression:
b == (c || d)
computes the value of (c || d), and the tests whether b is equal to the result of that subexpression.
A similar possible source of confusion is that
x < y < z
is not equivalent to
(x < y) && (y < z)
Rather, it's equivalent to
(x < y) < z
where the false or true (in C++) or 0 or 1 (in C) result of x < y is compared to the value of z.