Define an Optional Parameter in C++ Functions

Hi. I want to create a function with Optional parameters.
I know this feature is not available in C++. But i heard that i can use a handmade class called Optional (For example). But i don't know how to create a class that does my job. I know the Class Declaration , but i don't know how to create an optional item using C++ Classes.
What should i write in this Code ?
1
2
3
4
class Optional()
{
   
};
Last edited on
I would recommend using default values or function overloads.

1
2
3
4
5
6
//Default value
int foo(int bar, int optional = 0);

//Overloads
int bar(int foo);
int bar(int foo, int optional);


EDIT:
Maybe I'm not entirely sure what you're wanting.
Last edited on
1. I didn't got it.
2. I want to use my own class. Not built-ins.
I'm new to the term 'Optional Parameter' but I think I have the gist of it. Here is the page I am founding my admittedly limited understanding of this concept on: http://msdn.microsoft.com/en-us/library/dd264739.aspx

Following that example I would make a struct called "BMI" with two members; 'height' and 'weight' and probalby a member function 'calculate'.
1
2
3
4
5
6
7
struct BMI
{
      double calculate();

      double height;
      double weight;
}

I would say use a struct because this is a simple class, in more complex cases you would want to encapsulate your data.
The C++ way of doing this is called the Named Parameter Idiom.
You can read more about it here: http://www.parashift.com/c++-faq/named-parameter-idiom.html

Here's the MS article's code using NPI:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
#include <iostream>

struct CalculateBMI
{
  CalculateBMI( int weight = 0, int height = 0 ): 
    m_weight( weight ),
    m_height( height )
    { }
    
  CalculateBMI& weight( int weight ) { m_weight = weight; return *this; }
  CalculateBMI& height( int height ) { m_height = height; return *this; }
    
  operator int () const
  {
    return (m_weight * 703) / (m_height * m_height);
  }
  
private:
  int m_weight, m_height;
};

int main()
{
  std::cout << "CalculateBMI( 123, 64 )                   --> " << CalculateBMI( 123, 64 )                   << "\n";
  std::cout << "CalculateBMI().weight( 123 ).height( 64 ) --> " << CalculateBMI().weight( 123 ).height( 64 ) << "\n";
  std::cout << "CalculateBMI().height( 64 ).weight( 123 ) --> " << CalculateBMI().height( 64 ).weight( 123 ) << "\n";
  std::cout << "CalculateBMI( 123 ).height( 64 )          --> " << CalculateBMI( 123 ).height( 64 )          << "\n";
}

The limitation is that there is no compile time way to guarantee that all required arguments are present (not without a lot of template macro programming).

There do exist other, more esoteric ways to do this, such as:
http://www.boost.org/doc/libs/release/libs/parameter/doc/html/index.html
http://justinvh.blogspot.com/2012/10/c11-named-parameters-using-operator.html

(The Boost version is most like what you are looking for.)

And there's this version, which I can't seem to find quickly on Google. If you do find it I'm sure it will be more sophisticated than mine:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
#include <iostream>

enum class bmi { weight, height };

int CalculateBMI( int weight, int height )
{
  return (weight * 703) / (height * height);
}
int CalculateBMI( int weight, bmi h, int height )
{
  if (h == bmi::height) return CalculateBMI( weight, height );
  return 0;
}
int CalculateBMI( bmi a1, int v1, bmi a2, int v2 )
{
  if (a1 == a2) return 0;
  if (a1 == bmi::height) return CalculateBMI( v2, v1 );
  return CalculateBMI( v1, v2 );
}

int main()
{
  std::cout << "CalculateBMI( 123, 64 )                           --> " << CalculateBMI( 123, 64 )                           << "\n";
  std::cout << "CalculateBMI( 123, bmi::height, 64 )              --> " << CalculateBMI( 123, bmi::height, 64 )              << "\n";
  std::cout << "CalculateBMI( bmi::weight, 123, bmi::height, 64 ) --> " << CalculateBMI( bmi::weight, 123, bmi::height, 64 ) << "\n";
  std::cout << "CalculateBMI( bmi::height, 64, bmi::weight, 123 ) --> " << CalculateBMI( bmi::height, 64, bmi::weight, 123 ) << "\n";
}

Finally, there does exist a proposal for language support (in terms of syntax) for this kind of thing:
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2014/n4172

Hope this helps.
Need to take care of alignment requirements of the type.
alignas(T) char data[sizeof(T)];

Out of curiosity, what negative effects are present if alignment is not considered? Just loss of efficiency?
> what negative effects are present if alignment is not considered? Just loss of efficiency?

On some implementations (eg. Intel processors, without MMX/SSE), nothing more than a performance penalty.
On others, the consequences can be much more dire (with the most benevolent being immediate termination of the program with a 'bus error').

In C++, alignment is a fundamental property of the type.
Object types have alignment requirements which place restrictions on the addresses at which an object of that type may be allocated. ... An object type imposes an alignment requirement on every object of that type; ...
You can try this :
1
2
3
4
Void function(int x, int y ...)
{
...
}

The three dots in parameters imply any other parameters passed after x and y can be used in the function but aren't necessary. It works fine in Turbo, I don't know about the others.
Don't forget the comma:

 
#include <cstdarg> 
1
2
3
4
5
6
7
void function(int x, int y, ...)
{
  va_list args;
  va_start(args,y);
  ...
  va_end(args);
}

The problem with this is that you have to know additional information, like how many arguments there are and their types, in order to process them.


But you make me think...
with a class and a little template magic combined with some macro magic, you could do something.

I'm gonna play with it a moment.

[edit] Well, I can get syntax like f( -7, b=9, a = 12 ), but I'm not going to spend any more time on it right now.
Last edited on
Topic archived. No new replies allowed.