14

Here is a declaration of nullptr_t in <cstddef> :

namespace std {
  typedef decltype(nullptr) nullptr_t;
}

According to this, std::nullptr_t is an alias for some unspecified fundamental type of which nullptr is an instance. So the actual type of nullptr doesn't have a name (well, the language does not give it a name, the name was given by standard library).

nullptr itself is a keyword. But standard did not introduce a keyword for type of nullptr. Instead using decltype(nullptr) is offered.

What are reasons for doing this? I found it much confusing. You need to include header and specify std:: for just using a language built-in feature.

Is this to keep the set of C++ keywords as small as possible? Is this specifically for nullptr or committee is going to declare all new types like this, so we would have namespace std { typedef decltype(false) bool; } if such decision was made earlier?

3
  • 2
    Yes, nothing breaks existing code worse than adding new keywords to a language. Contextual keywords like enum class, final, override are a decent alternative btw. Commented Dec 5, 2015 at 16:06
  • But it's also the easiest thing to detect and fix (of course there are always pathological cases, e.g. code generation). Cosidering this, there are probably a myriad worse ways to break existing code. Commented Dec 5, 2015 at 16:14
  • Adding new keywords introduces potential breaks for existing code which the committee tries to avoid if possible. See Why are override and final identifiers with special meaning instead of reserved keywords? for the rationale for not making override and final reserved words. Commented Dec 5, 2015 at 17:46

3 Answers 3

11

According to the initial proposal of nullptr, N2431 (Emphasis Mine):

We propose a new standard reserved word nullptr. The nullptr keyword designates a constant rvalue of type decltype(nullptr). We also provide the typedef: typedef decltype(nullptr) nullptr_t; nullptr_t is not a reserved word. It is a typedef (as its _t typedef indicates) for decltype(nullptr) defined in <cstddef>. We do not expect to see much direct use of nullptr_t in real programs.

Generally, the committee is reluctant in the addition of new keywords in the language. In my humble opinion this is for a good reason, named backward compatibility.

If you further read the proposal, you'd realize that the main concern is not breaking existing code.

Imagine the effect that would have if the committee now and then introduced a new keyword. All hell would break loose and C++ from a success story would have been a big joke.

4
  • 3
    However new keyword for nullptr was added. I'm sure it has higher chances that someone already used nullptr in their code than used nullptr_t because "We do not expect to see much direct use of nullptr_t in real programs."
    – anton_rh
    Commented Dec 5, 2015 at 16:43
  • so new types are expected to be added to std namespace?
    – anton_rh
    Commented Dec 5, 2015 at 16:44
  • @anton_rh They proposed nullptr to be a keyword. "We propose a new standard reserved word nullptr.". The name was chosen after an informal pole and google search. Commented Dec 5, 2015 at 16:48
  • 2
    @anton_rh Trust the committee they're wise. They have to consider things that we are not aware of and make the best compromise out of them. Commented Dec 5, 2015 at 16:50
3

I believe the reason is simple: the standardization committee wants to avoid as much as reasonably possible to introduce new keywords (because, given the billions lines of existing C++ code, it is likely to conflict with some code somewhere).

Since std::nullptr_t is definable, it does not need to be a keyword.

And bool is a keyword for historical reasons. It very probably has been introduced quite early...

C++ is mostly about legacy software, so human and social and economical considerations (and backward compatibility) matters a lot for the standardization committee (often more than technical reasons alone).

2
  • 3
    we can avoid using keywords at all. Just use std:: for everything. std::int int = 10, while = 0; std::while(int > while) ...
    – anton_rh
    Commented Dec 5, 2015 at 16:08
  • 1
    But the C++ committee did not want that. FWIW PL/1 is a language without keywords, so IF IF=THEN THEN ELSE=IF; is valid in PL/1 but unreadable Commented Dec 5, 2015 at 16:45
3

Adding new keywords are avoided when not necessary. Why add something to the language when it can just be added to the library.

You already have a similar thing with sizeof(x) which returns std::size_t, which you also have to include a header to get the typedef for.

4
  • I thought that size_t is just a typedef to unsigned int or something else that is correct for the platform running code. No built-in features here.
    – anton_rh
    Commented Dec 5, 2015 at 16:19
  • @anton - Yes, std::size_t is a typedef, just like std::nullptr_t. :-) And the compiler can return a value of that type for sizeof, just like it can return a value for nullptr, even if none of the typedefs are visible. No difference!
    – Bo Persson
    Commented Dec 5, 2015 at 16:24
  • I was sure that size_t is mapped to existing named type (like unsigned int). That is difference. Though can't find it in stddef.h and become thinking it's magic too... O_o
    – anton_rh
    Commented Dec 5, 2015 at 16:36
  • Found a good thread that exposes analogy between std::nullptr_t and std::size_t: stackoverflow.com/a/20809166/5447906
    – anton_rh
    Commented Dec 5, 2015 at 17:18

Not the answer you're looking for? Browse other questions tagged or ask your own question.