About initializing C ++ class members

Source: Internet
Author: User

In the process of using C ++ programming, class members often need to be initialized. There are two common methods:

Method 1:

CMYClass::CSomeClass(){    x=0;    y=1;}

Method 2:

CSomeClass::CSomeClass() : x(0), y(1){}

This article will discuss the similarities and differences between the two methods and how to use them.

Technically speaking, the second method is better, but in most cases, there is actually no difference between the two. The second syntax is called the member initialization list. There are two reasons for using this syntax: one is that this is required, and the other is for efficiency.

Let's take a look at the first reason-necessity. Suppose you have a class member, which is a class or structure and has only one constructor with one parameter.

class CMember {public:    CMember(int x) { ... }};

Because cmember has an explicitly declared constructor, the compiler does not generate a default constructor (without parameters). Therefore, an instance of cmember cannot be created without an integer.

Cmember * PM = new cmember; // error !! Cmember * PM = new cmember (2); // OK

If cmember is a member of another class, how do you initialize it? The answer is that you must use the member initialization list.

Class cmyclass {cmember m_member; public: cmyclass () ;}; // The initialization list must be used to initialize the member m_membercmyclass: cmyclass (): m_member (2 ){•••}

There is no other way to pass the parameter to m_member, if the member is a constant object or reference is the same. According to the C ++ rules, constant objects and references cannot be assigned values. They can only be initialized.

The second reason for using the initialization list is for efficiency consideration when the member class has a default constructor and a value assignment operator. The cstring of MFC provides a perfect example. Suppose you have a cmyclass with a member m_str of the cstring type, and you want to initialize it as "Hi, how are you .". You have two options:

Cmyclass: cmyclass () {// use the value assignment operator // cstring: Operator = (lpctstr); m_str = _ T ("Hi, how are you .");}
// Use the initialization list // and constructor cstring: cstring (lpctstr) cmyclass: cmyclass (): m_str (_ T ("Hi, how are you. ")){}

Are there any differences between them? Yes. The compiler always ensures that all member objects are initialized before the constructor is executed. Therefore, the Code compiled in the first example calls cstring: cstring to initialize m_str, this is completed before the control reaches the value assignment statement. In the second example, the compiler generates a call to cstring: cstring (lpctstr) and passes "Hi, how are you." to this function. The result is that two cstring functions (constructor and value assignment operator) are called in the first example, and only one function is called in the second example.

In the cstring example, this does not matter, because the default constructor is inline. cstring only allocates memory for the string as needed (that is, when you actually assign values ). However, repeated function calls are a waste of resources, especially when constructors and value assignment operators allocate memory. In some large classes, you may have a constructor and an assignment operator that calls the same init function that allocates a large amount of memory. In this case, you must use the initialization list to avoid unnecessary memory allocation twice.

For ints, longs, or other types without constructor, there is no performance difference between the two methods in the initialization list and in the constructor body assignment. No matter which method is used, only one value assignment occurs. Some programmers say that you should always use the initialization list to maintain good habits, but I have never found any difficulty in converting the two methods as needed. In terms of programming style, I tend to use assignment in the subject, because there is more space for formatting and adding comments, you can write such a statement:

x=y=z=0;

Or

memset(this,0,sizeof(this));

Note that the second part is definitely not object-oriented.

When I consider the initialization list issue, there is a strange feature I should warn you that it is about C ++ initialization class members, they are initialized in the declared order, instead of following the order in the initialization list.

class CMyClass {    CMyClass(int x, int y);    int m_x;    int m_y;};CMyClass::CMyClass(int i) : m_y(i), m_x(m_y){}

You may think that the above Code will first do m_y = I, then m_x = m_y, and finally they have the same value. But the compiler first initializes m_x and then m_y, because they are declared in this order. The result is m_x, which will have an unpredictable value. This example is intentionally designed to illustrate this point, but this bug will naturally occur. There are two ways to avoid it. One is to declare members in the order you want them to be initialized, and the other is, if you decide to use the initialization list, these members are always listed in the order they are declared. This will help eliminate confusion.

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.