1

in python I can write:


def test(a, b=None):
    if b is None:
        return
    else:
        print(123)
    

in cpp, it's better to avoid pointers, so I use reference instead,

so how to do the same thing?

#include "stdio.h"
void test(int a, const int &b) { 
// how to check ?? since b should not be nullptr
printf("123\n"); };
int main() { test(); }

3 Answers3

3

in cpp, it's better to avoid pointers, so I use reference instead

References can't refer to NULL, so pointers are the traditional way to do this, e.g. void test(int a, const int *b=NULL). Much of the reason references are encouraged over pointers is because it saves you from handling NULL arguments; if you need NULL arguments, references aren't saving you from anything.

std::optional is sometimes used for similar scenarios, but it's much newer (C++17), and I don't think there is strong consensus on whether it's preferable; that said, using it with std::nullopt as the default is close to what you've got already, and a reasonable way to handle the problem.

The alternative (mentioned in the answers to the above linked question) is just to overload the function twice, once with the argument, and once without; this could be combined with the std::optional approach to allow simpler calling for users only passing one argument (with a default, the generated code inlines the creation of the default argument at each call site that relies on it), but still implementing the function via common code (the single argument function just turning around and calling the two-argument function).

ShadowRanger
  • 143,180
  • 12
  • 188
  • 271
0

C++ references cannot be NULL.They always point to valid object,initialised during their declaration.

0

As mentioned in the other answers, NULL references aren't allowed in C++, so you can't use NULL as a default value for a by-reference argument, and std::optional would be a good choice instead.

You can define your own sentinel-object though, to perform the same function as NULL without actually being a NULL-reference, like this:

#include "stdio.h"

const int & get_sentinel_ref()
{
   static int sentinel = 0;  // must be declared static
   return sentinel;          // in order to have a fixed address
}

void test(int a, const int &b = get_sentinel_ref())
{
   // Check if b is referring to our sentinel-value or not
   // Note that I'm comparing memory-addresses here, not values
   // otherwise the code would do the wrong thing if the user
   // passed in zero (or whatever dummy-value sentinel is set
   // to in the get_sentinel_ref() function above)
   if (&b == &get_sentinel_ref())
   {
      printf("a is %i, but you didn't supply a second argument!\n", a);
   }
   else
   {
      printf("a is %i, b is %i\n", a, b);
   }
}

int main(int, char **)
{
   test(5);
   test(6,7);
   return 0;
}

... When run, the above program prints:

a is 5, but you didn't supply a second argument!
a is 6, b is 7
Jeremy Friesner
  • 70,199
  • 15
  • 131
  • 234