What does casting to `void` really do?
Casting to void is used to suppress compiler warnings. The Standard says in §5.2.9/4 says,
Any expression can be explicitly converted to type “cv void.” The
expression value is discarded.
C++ What is the purpose of casting to void?
Multiple purposes depending on what you cast
- Marking your intention to the compiler that an expression that is entirely a no-op is intended as written (for inhibiting warnings, for example)
- Marking your intention to to the compiler and programmer that the result of something is ignored (the result of a function call, for example)
- In a function template, if a return type is given by a template parameter type
T
, and you return the result of some function call that could be different fromT
in some situation. An explicit cast toT
could, in thevoid
case, prevent a compile time error:
int f() { return 0; } void g() { return (void)f(); }
- Inhibiting the compiler to choose a comma operator overload (
(void)a, b
will never invoke an overloaded comma operator function).
Note that the Standard guarantees that there will never be an operator void()
called if you cast a class object to void
(some GCC versions ignore that rule, though).
Purpose of casting a struct pointer to void without using the result
(void)bh;
has no effect in the generated code. However, with many compilers it will prevent the compiler from issuing a warning about the parameter bh
not being otherwise used in the function, and that was almost certainly the intent of the programmer. bh
being a struct pointer is irrelevant; if this technique works at all, it will work regardless of the type of the unused parameter.
C++ has a more elegant way to accomplish this, allowing you to omit the variable name for any argument you don't need --
static unsigned
parent(const struct binheap *, unsigned u)
{
return (u / 2);
}
-- but C doesn't support this. Some compilers have extensions for the same purpose that are, if not so elegant, at least more self-describing, e.g. GCC's
static unsigned
parent(const struct binheap *bh __attribute__((unused)), unsigned u)
{
return (u / 2);
}
The (void)bh;
trick is the only technique for suppressing unused-parameter warnings that uses only the facilities of ISO C; on the other hand, it's not guaranteed to work, the warnings a compiler emits are entirely up to that compiler, so you're already in implementation-defined territory no matter what you do.
Casting function returns to void
It explicitly means you ignore the return value, and did not just forget it.
Why cast free's return value to void?
If we are talking about the standard free
function then its prototype is
void free(void *ptr);
Therefore the cast is completely useless.
Now some speculation.
The author might have forgotten to include the stdlib.h
header declaring this prototype, so the compiler is assuming the return type of it as int
. Now during static analysis of this code the compiler was warning about the unused return value of what it thinks to be a non-void
function. Such a warnings are usually silenced by adding the cast to void
.
Casting to void (not pointer) is allowed, why?
Casting to void simply discards the result of the expression. Sometimes, you'll see people using this to avoid "unused variable" or "ignored return value" warnings.
In C++, you should probably write static_cast<void>(expr);
rather than (void)expr;
This has the same effect of discarding the value, while making it clear what kind of conversion is being performed.
The standard says:
Any expression can be explicitly converted to type cv void, in which
case it becomes a discarded-value expression (Clause 5). [ Note:
however, if the value is in a temporary object (12.2), the destructor
for that object is not executed until the usual time, and the value of
the object is preserved for the purpose of executing the destructor.
—end note ]
ISO/IEC 14882:2011 5.2.9 par. 6
Type casting a variable to void?
This is to avoid unused variable warnings in some compilers.
Also there is a MISRA rule which states that all function parameters must be used. This method is a workaround for this rule.
What effect does casting a variable as (void *) have?
void*
is the universal data pointer type, that, when used as an argument type, denotes that a function works on "bare" memory blocks. It cannot be dereferenced.
Any other data pointer type can be implicitly converted to void*
, so the explicit cast is probably either wrong (unnecessary), or a workaround for a broken compiler, or a shorthand to cast to unsigned char *
(in which case it's a workaround for a broken interface).
Is casting a function return to void an old-style-cast or not?
It's fine.
(void) f(x);
is always equivalent to a static_cast
as per [expr.static.cast]/6
:
Any expression can be explicitly converted to type cv void, in which case it becomes a discarded-value expression.
Converting the result of a function to void
is the way to make an expression a discard-value-expression. Now, the C++ way should be static_cast<void>(...)
but (void) ...
is an idiom (and is shorter).
Since the latter is well-defined and really common in codebases, gcc1 and clang2 made it not trigger Wold-style-cast
.
It's well-defined, recognized by major compilers. It's fine.
1) g++ documentation --- 3.5 Options Controlling C++ Dialect
-Wold-style-cast
(C++ and Objective-C++ only)
Warn if an old-style (C-style) cast to a non-void type is used within a C++ program. The new-style casts (dynamic_cast
,static_cast
,reinterpret_cast
, andconst_cast
) are less vulnerable to unintended effects and much easier to search for.
2) not documented
Related Topics
How to Find Where an Exception Was Thrown in C++
C/C++ Function Definitions Without Assembly
Are C++ Templates Just MACros in Disguise
How to Give Priority to Privileged Thread in Mutex Locking
When Should You Use the "This" Keyword in C++
Why Is Std::Min Failing When Windows.H Is Included
C++ Lambdas How to Capture Variadic Parameter Pack from the Upper Scope
C++ Singleton VS. Global Static Object
How to Use _Crt_Secure_No_Warnings
How to Create a Function Dynamically, During Runtime in C++
Return a "Null" Object If Search Result Not Found
How to Get the Gl Library/Headers
Cmake: Include Library Dependencies in a Static Library
What Is Data Alignment? Why and When Should I Be Worried When Typecasting Pointers in C
Why Do Some People Use Swap for Move Assignments
Why Is "!=" Used with Iterators Instead of "<"
C++:Creating an Array with a Size Entered by the User
How to Truncate a Floating Point Number After a Certain Number of Decimal Places (No Rounding)