Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why is C++'s void type only half-heartedly a unit type?

Tags:

c++

types

C++'s void type is not uninhabited. The problem is that while it has precisely one inhabitant, very much like the Unit type (a.k.a. ()) in ML-like languages, that inhabitant cannot be named or passed around as an ordinary value. For example, the following code fails to compile:

void foo(void a) { return; }
void bar() { foo(foo()); }

whereas equivalent (say) Rust code would compile just fine:

fn foo(a : ()) { return; }
fn bar() { foo(foo(())); }

In effect, void is like a unit type, but only half-heartedly so. Why is this the case?

Does the C++ standard explicitly state that one cannot create values of type void? If yes, what is the rationale behind this decision? If not, why does the code above not compile?

If it is some backwards-compatibility related reason, please give a code example.

To be clear, I'm not looking for work-arounds to the problem (e.g. using an empty struct/class). I want to know the historical reason(s) behind the status quo.

EDIT: I've changed the syntax in the code examples slightly to make it clear that I'm not trying to hijack existing syntax like void foo(void) (consequently, some comments may be out of date). The primary motivation behind the question is "why is the type system not like X" and not "why does this bit of syntax not behave as I'd like it to". Please keep this point in mind if you're writing an answer talking about breaking backwards compatibility.

like image 865
typesanitizer Avatar asked Aug 16 '18 01:08

typesanitizer


People also ask

What data type is void in C?

The void type, in several programming languages derived from C and Algol68, is the type for the result of a function that returns normally, but does not provide a result value to its caller.

What is the type of a void function?

Void functions are created and used just like value-returning functions except they do not return a value after the function executes. In lieu of a data type, void functions use the keyword "void." A void function performs a task, and then control returns back to the caller--but, it does not return a value.

What is void C?

What is void in C programming? It means “no type”, “no value” or “no parameters”, depending on the context. We use it to indicate that: a function does not return value. a function does not accept parameters.

What does void type return?

A void return type simply means nothing is returned.


1 Answers

That is really an historical question. Old (pre-C) language used to differentiate functions which returned values, from subroutines which did not (ooh, the good old taste of Fortran IV and Basic...). AFAIK, early C only allowed functions, simply functions were by default returning int and it was legal to have no return statement (mean return an unspecified value) and legal to ignore any return value - so that the programmer can write coherent code... In those early days, C was used more or less as a powerful macro assembler, and anything was allowed provided the compiler can translate it into machine instructions (no strict aliasing rule for example...). As the memory unit was char, no need for void * pointer, char * was enough.

Then people felt the need to make clear that a buffer was expected to contain anything and not a character string, and that some functions will never return a value. And void came to feel the gap.

The drawback, is that when you declare a void function, you declare what was called a subroutine, that is something that can never be used as a value, in particular never be used as a function parameter. So void is not only a special type that can never be instantiated, it really declare that the result cannot be a member of an expression.

And because of language inheritance, and because the C standard library is still a subset of the C++ standard one, C++ still processes void the way ANSI C did.

Other languages can use different conventions. In Python for example a function will always return something, simply it returns the special None value if no return statement is encountered. And rust seem to have still another convention.

like image 187
Serge Ballesta Avatar answered Nov 14 '22 18:11

Serge Ballesta