HÀM TẠO VÀ HÀM HỦY TRONG C++

Hàm destructor (hàm hủy) là 1 một số loại hàm member đặc biệt không giống của class, được triển khai khi 1 đối tượng của class đó bị bỏ. Trong lúc các hàm constructors (hàm khởi tạo) được thiết kế với để có thể tạo một class, thì những hàm destructors (hàm hủy) được thiết kế theo phong cách để hỗ trợ vấn đề dọn dẹp và sắp xếp bộ nhớ.

Bạn đang xem: Hàm tạo và hàm hủy trong c++

lúc một đối tượng người tiêu dùng ở ngoại trừ phạm vi vùng code mà lại công tác đang làm việc một bí quyết thông thường, hoặc lúc một đối tượng được cấp phép rượu cồn bị xóa sổ một bí quyết tường minc bởi từ bỏ khóa delete, thì hàm destuctor của class đã auto được Call (nếu như nó tồn tại) nhằm tiến hành bất kỳ câu hỏi lau chùi bộ nhớ cần thiết nào trước lúc xóa bỏ thay đổi tượng ngoài bộ nhớ. Đối với các class đơn giản (phần lớn class mà chỉ khởi sản xuất cực hiếm của những biến thành viên nằm trong các hình dáng dữ liệu cơ bản) thì không nhất thiết phải áp dụng hàm destructor vày C++ đã auto lau chùi và vệ sinh bộ nhớ cho bạn.

Tuy nhiên, trường hợp đối tượng trực thuộc class của người tiêu dùng sẽ sở hữu bất kỳ tài nguyên nào (ví dụ như: bộ nhớ hễ, hoặc một tệp tin, giỏi database handle) cần được giải pchờ, hoặc nếu bạn phải triển khai ngẫu nhiên tác vụ bảo trì làm sao trước khi đối tượng bị diệt, thì hàm destructor đó là khu vực tuyệt đối để triển khai hồ hết vấn đề này, cũng chính vì nó thường là chỗ cơ mà code được triển khai sau cuối, trước lúc đối tượng người dùng bị diệt.


Nội dung chính


1. Việc viết tên đến hàm destructor

Giống như các hàm constructor, các hàm destructors cũng đều có các luật lệ đánh tên riêng:


Hàm destructor buộc phải gồm thuộc thương hiệu với class, với thêm vết bổ làm cho tiền tố.Hàm destructor chẳng thể thừa nhận vào các đối số.Hàm destructor không có hình dáng tài liệu trả về.

Lưu ý, Chỉ sống thọ độc nhất một hàm destructor bên trong mỗi class, do đó không tồn tại phương pháp làm sao để overload (hấp thụ chồng) các hàm destructors, bởi vì bọn chúng bắt buộc được riêng biệt với nhau dựa trên các đối số truyền vào.

Nói phổ biến chúng ta không nên được gọi tường minch bất kể hàm destructor như thế nào (cũng chính vì bọn chúng sẽ tiến hành Hotline auto khi đối tượng người dùng bị diệt đi), bởi vì hiếm hoi lúc chạm chán buộc phải gần như ngôi trường hợp đề nghị dọn dẹp và sắp xếp một đối tượng người tiêu dùng nhiều hơn thế một lượt. Tuy nhiên, các hàm destructor có thể Gọi đến những hàm thành viên không giống một giải pháp an toàn, chính vì đối tượng người sử dụng đã không xẩy ra bỏ cho tới sau khi hàm destructor được tiến hành ngừng.

2. Một ví dụ về hàm destructor

Chúng ta thuộc coi một class đơn giản dễ dàng có áp dụng hàm destructor:

/*** millionarthur.mobi - Kênh công bố IT hàng đầu Việt Nam**
author millionarthur.mobin* Contact: millionarthur.mobin

Nếu bạn test biên dịch đoạn code bên trên với bị lỗi sau:


If you compile the above example and get the following error:error: "class IntArray" has pointer data members <-Werror=effc++>|error: but does not override "IntArray(const IntArray&)" <-Werror=effc++>|error: or "operator=(const IntArray&)" <-Werror=effc++>|Để xung khắc phúc lỗi này, chúng ta có thể vứt bỏ cờ “-Weffc++” khỏi compile settings (đều tùy chỉnh về biên dịch) cho ví dụ này, hoặc là chúng ta có thể thêm nhị chiếc code sau vào trong class IntArray:

IntArray(const IntArray&) = delete;IntArray& operator=(const IntArray&) = delete;Chúng ta đang bàn bạc về tính năng của hai câu lệnh này trong chương thơm sau.

Đoạn công tác bên trên đang in ra:

The value of element 5 is: 6Trên cái đầu tiên, bọn họ vẫn khởi tạo một đối tượng bắt đầu của class IntArray, được Call là ar, và truyền vào độ dài mảng là 10. Việc khởi tạo này đang Gọi cho hàm constructor nhằm mục đích cấp phát bộ nhớ lưu trữ động cho những trở thành viên của class IntArray. Chúng ta buộc phải sử dụng cấp phép động trên trên đây cũng chính vì chúng ta cần thiết hiểu rằng tại thời điểm biên dịch (compile time) thì độ lâu năm của mảng là từng nào (caller – đối tượng Hotline hàm đang quyết định điều đó).

Xem thêm: Hướng Dẫn Cài Đặt Autocad 2014 Bản Full Active + Hướng Dẫn Cài Đặt

lúc hàm main() hoàn thành, bây giờ đối tượng người tiêu dùng ar sẽ ở ko kể phạm vi đoạn code nhưng lịch trình đang chạy bên trên kia (có nghĩa là ar đã goes out of scope). Như vậy sẽ làm cho hàm destructor ~IntArray() được Gọi, để xóa đi mảng mà lại họ đang cấp phát phía bên trong phần thân hàm của constructor!

3. Tính tân oán thời gian Hotline hàm constructor với hàm destructor

Như đã đề cập trước kia, hàm constructor sẽ tiến hành Hotline lúc một đối tượng người sử dụng được tạo nên, với hàm destructor sẽ được điện thoại tư vấn lúc một đối tượng người tiêu dùng bị bỏ đi. Trong ví dụ dưới đây, chúng ta đã sử dụng câu lệnh cout bên trong hàm constructor cùng hàm destructor để triển khai rõ điều này:

/*** millionarthur.mobi - Kênh ban bố IT số 1 Việt Nam**
author millionarthur.mobin* Contact: millionarthur.mobin

Constructing Simple 11Constructing Simple 22Destructing Simple 2Destructing Simple 1Lưu ý rằng “Simple 1” bị bỏ trước “Simple 2” bởi vì bọn họ đang xóa đối tượng người dùng pSimple trước lúc hàm main() xong, trong khi đối tượng người tiêu dùng simple chỉ bị hủy đi sau khi hàm main() đang xong rồi.

Các biến chuyển cục bộ bên trong class thì số đông được khởi tạo/thi công trước khi

hàm main() được tiến hành, với được hủy đi sau khoản thời gian hàm main() sẽ xong xuôi rồi.


4. RAII

RAII (Resoure Acquisition Is Initialization – tạm dịch, Việc thu hồi tài nguim chính là khi khởi tạo) là 1 trong những kỹ thuật lập trình nhưng mà trong đó bài toán thực hiện tài ngulặng được gắn sát cùng với vòng đời của các đối tượng người tiêu dùng tất cả thời lượng mãi sau được giải pháp xử lý tự động (ví dụ, non-dynamically allocated objects – các đối tượng được cấp phát tĩnh). Trong C++, RAII được thiết đặt trải qua các classes với những hàm constructors và destructors. Một tài nguyên ổn (ví dụ như bộ lưu trữ, một file, tuyệt database handle, v.v…) thường được tích lũy bên phía trong phần thân hàm của constructor của đối tượng người tiêu dùng (tuy vậy nó có thể được thu thập sau khoản thời gian đối tượng được tạo thành, ví như điều ấy vừa lòng lý). Tài nguim này tiếp nối rất có thể được thực hiện trong lúc đối tượng người sử dụng vẫn đang còn sống. Khi đối tượng bị hủy, tài nguim này cũng trở thành được giải phóng bên phía trong hàm destructor. Ưu điểm chính của RAII là nó góp ngăn chặn câu hỏi rò rỉ tài nguyên (ví dụ: Sở lưu giữ không được giải phóng) lúc tất cả những đối tượng đã sở hữu tài nguyên đông đảo được dọn dẹp vệ sinh không bẩn một bí quyết tự động.

Theo mô hình RAII, những đối tượng người dùng đang sở hữu tài ngulặng tránh việc được cấp phép động. Như vậy là do những hàm destructors chỉ được Hotline khi một đối tượng người sử dụng được bỏ đi. Đối cùng với các đối tượng được cấp phát bên trên vùng ghi nhớ stack, điều đó vẫn tự động hóa ra mắt khi đối tượng người tiêu dùng nằm ngoại trừ phạm vi đoạn code nhưng chương trình đang chạy trên kia (goes out of scope), cho nên, không nhất thiết phải lo lắng về câu hỏi các tài nguim cho đến thời khắc sau cùng đạt được dọn dẹp vệ sinh sạch mát hay không. Tuy nhiên, đối với các đối tượng người tiêu dùng được cấp phát hễ, tín đồ dùng/thiết kế viên yêu cầu bao gồm trách nhiệm giải pđợi những tài ngulặng sau thời điểm đã áp dụng dứt – Nếu quên làm cho vấn đề đó, thì hàm destructor sẽ không được call, dẫn đến sự việc phần bộ lưu trữ giành riêng cho đối tượng người dùng của class cùng tài nguim mà lại nó đã quản lí lý/nắm giữ bị rò rỉ!

Class IntA ở đầu bài học này là 1 ví dụ về một class gồm cài đặt RAII – triển khai cấp phát bộ lưu trữ bên phía trong hàm constructor, với giải pngóng bộ lưu trữ bên trong hàm destructor. std::string với std::vector là các ví dụ về mọi class phía bên trong thư viện standard mà lại tuân theo RAII – bộ nhớ lưu trữ đụng được đem Lúc khởi tạo, cùng được tự động hóa dọn sạch sẽ lúc thực hiện quá trình diệt.

Quy tắc: Nếu class của công ty bắt buộc cấp phép bộ lưu trữ động, hãy thực hiện quy mô RAII, chứ đừng nên cấp phát cồn trực tiếp đến những đối tượng của class của khách hàng.

5. Lưu ý về hàm exit()

Hãy để ý rằng trường hợp sử dụng hàm exit(), công tác của các bạn sẽ dứt với sẽ không tồn tại hàm destructors làm sao được điện thoại tư vấn. Hãy bình an nếu như khách hàng vẫn sử dụng cùng dựa vào những hàm destructors để triển khai những các bước lau chùi cần thiết (ví dụ như: Viết gì đó vào trong 1 file log hoặc đại lý dữ liệu, trước khi bay chương trình).

6. Tổng kết

Bạn thấy đấy, Khi những hàm constructors với các hàm destructors được áp dụng cùng với nhau, các class của các bạn sẽ tự động hóa khởi tạo nên cùng vệ sinh sau khi chúng được thực hiện ngừng nhưng không yêu cầu lập trình sẵn viên bắt buộc thực hiện bất kỳ quá trình đặc trưng nào! Vấn đề này có tác dụng bớt Tỷ Lệ tạo ra bug (lỗi), với làm cho những class dễ áp dụng rộng.