Logical value of an assignment in C
-
11-09-2019 - |
Question
while (curr_data[1] != (unsigned int)NULL &&
((curr_ptr = (void*)curr_data[1]) || 1))
Two part question.
What will (curr_ptr = (void*)curr_data[1])
evaluate to, logically. TRUE
?
Also, I know its rather hack-ish, but is the while
statement legal C? I would have to go through great contortions to put the assignment elsewhere in the code, so I'd be really nice if I could leave it there, but if it's so egregious that it makes everyone's eyeballs burst into flames, I'll change it.
Solution
To answer your questions:
- It will evaluate to true if
curr_ptr
isn't set toNULL
(i.e.curr_data[1]
isn't 0). - I believe it's legal, but there are bigger problems with this line of code.
Anyway, I'm assuming you didn't write this code, because you're debating about leaving it in vs. taking it out. So I want you to find out who wrote this line of code and introduce them to a heavy blunt object.
(unsigned int)NULL
is ridiculous. Why would you do this? This will probably be the same as just writing0
(not sure if that's guaranteed by the standard).- What kind of data is in
curr_data[1]
if it's being cast to a pointer (and pointers are being cast to it)? If it's supposed to be holding a pointer as an integral type, you should use the typeintptr_t
oruintptr_t
provided in<stdint.h>
for that purpose (if you're compiler doesn't support C99ptrdiff_t
may be an acceptable substitute). - The
|| 1
at the end seems to be redundant. Ifcurr_ptr = (void*)curr_data[1]
would have evaluated to false, we would have caught that in the first condition.
It may be a pain in the ass, but seriously reconsider rewriting this line. It looks like an entry in the IOCCC.
OTHER TIPS
(curr_ptr = (void*)curr_data[1])
will evaluate to TRUE unless it is a null pointer.
Assuming that curr_data
is an array of pointers, and what you want to do is to run the loop while the second of these pointers is not null, while assigning its value to curr_ptr
, I would do:
while ((curr_ptr = (void*)curr_data[1]) != NULL) { ... }
Assignments are expressions in C, so what you have works. Changing the ;
to {}
means the exact same thing and is much clearer, do that change at the very least. Assignments in conditions should be avoided when you have a clearer alternative (which is usually true), but if this is clearest in this place, then use it.
The result of an assignment is the assigned-to object. a = value
will do the assignment and then evaluate to a
. This is used to do things like a = b = 0
.
To further clean up the code, there's no need for the void cast, and if this is chars, use '\0' (the null character) instead of NULL (which is supposed to be used with pointers only).
You wouldn't have to go through "great contortions", that is completely equivalent to
while (curr_data[1]) {
curr_ptr = (void *)curr_data[1];