template<class T>
class Node
{
public:
Node(Node<T>* next=NULL, T data=T()) : _next(next), _data(data)
{
}
Node<T>* _next;
T _data;
};
I'm new to c++ template. For default parameters, is T data = T()
the standard way to do it? Maybe T data = 0
is ok too?
There are two ways to initialize a class object: Using a parenthesized expression list. The compiler calls the constructor of the class using this list as the constructor's argument list. Using a single initialization value and the = operator.
Destructors and copy constructors cannot be templates. If a template constructor is declared which could be instantiated with the type signature of a copy constructor, the implicitly-declared copy constructor is used instead.
An object of type std::initializer_list<T> is a lightweight proxy object that provides access to an array of objects of type const T .
A default constructor is a constructor that either has no parameters, or if it has parameters, all the parameters have default values. If no user-defined constructor exists for a class A and one is needed, the compiler implicitly declares a default parameterless constructor A::A() .
That's not "constructor initialization", that's a default parameter. It allows the caller to provide fewer arguments than the function has, the unspecified arguments will take on the default value.
Another way to do it would be:
template<class T>
class Node
{
public:
Node(Node<T>* next, T data) : m_next(next), m_data(data) {}
Node(Node<T>* next) : m_next(next), m_data() {}
Node(void) : m_next(NULL), m_data() {}
Node<T>* m_next;
T m_data;
};
Where using fewer than two arguments is also allowed, but calls different constructors (that have almost the same behavior).
There are a number of advantages to using separate overloads:
data
parameter is always omitted.data
parameter is always provided.This really has nothing to do with constructors; what you're seeing is a combination of default function arguments and value-initialization.
The latter is described in the C++03 standard, §8.5/5:
To value-initialize an object of type T means:
- if T is a class type (clause 9) with a user-declared constructor (12.1), then the default constructor for T is called (and the initialization is ill-formed if T has no accessible default constructor);
- if T is a non-union class type without a user-declared constructor, then every non-static data member and base-class component of T is value-initialized;
- if T is an array type, then each element is value-initialized;
- otherwise, the object is zero-initialized
and
To zero-initialize an object of type T means:
- if T is a scalar type (3.9), the object is set to the value of 0 (zero) converted to T;
- if T is a non-union class type, each nonstatic data member and each base-class subobject is zero-initialized;
- if T is a union type, the object’s first named data member89) is zero-initialized;
- if T is an array type, each element is zero-initialized;
- if T is a reference type, no initialization is performed.
And lastly, piecing it together, §8.5/7:
An object whose initializer is an empty set of parentheses, i.e., (), shall be value-initialized.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With