Skip to content

Commit f899b6d

Browse files
author
Colin Robertson
committed
Acrolinx, blockers
1 parent 5ce8206 commit f899b6d

File tree

2 files changed

+13
-9
lines changed

2 files changed

+13
-9
lines changed

docs/cpp/object-lifetime-and-resource-management-modern-cpp.md

Lines changed: 10 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -7,9 +7,13 @@ ms.assetid: 8aa0e1a1-e04d-46b1-acca-1d548490700f
77
---
88
# Object lifetime and resource management (RAII)
99

10-
Unlike managed languages, C++ has no garbage collection process that releases heap memory and other resources as a program runs. A program is responsible for returning all acquired resources to the operating system. Failure to release a resource results in a *leak* and renders the resource unavailable to other programs. Memory leaks in particular are a common cause of bugs in C-style programming. Modern C++ avoids using heap memory as much as possible by declaring objects on the stack. When an resource is too large for the stack, then it should be *owned* by an object that is responsible for releasing the resource in its destructor. The principle that *objects own resources* is also known as "resource acquisition is initialization" or "RAII". The owning object itself is declared on the stack, so that when the goes out of scope, its destructor is automatically invoked. In this way, garbage collection in C++ is closely related to object lifetime and is deterministic. A resource is always released at a known point in the program, which you can control. Only deterministic destructors like those in C++ can handle memory and non-memory resources equally.
10+
Unlike managed languages, C++ doesn't have automatic *garbage collection*. That's an internal process that releases heap memory and other resources as a program runs. A C++ program is responsible for returning all acquired resources to the operating system. Failure to release an unused resource is called a *leak*. Leaked resources are unavailable to other programs until the process exits. Memory leaks in particular are a common cause of bugs in C-style programming.
1111

12-
The following example shows a simple object `w`. It is declared on the stack at function scope, and is destroyed at the end of the function block. The object `w` owns no *resources* (such as heap-allocated memory). Its only member `g` is itself declared on the stack and simply goes out of scope along with `w`. Therefore, no special code is needed in the `widget` destructor.
12+
Modern C++ avoids using heap memory as much as possible by declaring objects on the stack. When a resource is too large for the stack, then it should be *owned* by an object. As the object gets initialized, it acquires the resource it owns. The object is then responsible for releasing the resource in its destructor. The owning object itself is declared on the stack. The principle that *objects own resources* is also known as "resource acquisition is initialization," or RAII.
13+
14+
When a resource-owning stack object goes out of scope, its destructor is automatically invoked. In this way, garbage collection in C++ is closely related to object lifetime, and is deterministic. A resource is always released at a known point in the program, which you can control. Only deterministic destructors like those in C++ can handle memory and non-memory resources equally.
15+
16+
The following example shows a simple object `w`. It's declared on the stack at function scope, and is destroyed at the end of the function block. The object `w` owns no *resources* (such as heap-allocated memory). Its only member `g` is itself declared on the stack, and simply goes out of scope along with `w`. No special code is needed in the `widget` destructor.
1317

1418
```cpp
1519
class widget {
@@ -30,7 +34,7 @@ void functionUsingWidget () {
3034
// as if "finally { w.dispose(); w.g.dispose(); }"
3135
```
3236
33-
In the following example, `w` owns a memory resource and therefore must have code in its destructor to delete the memory.
37+
In the following example, `w` owns a memory resource and so must have code in its destructor to delete the memory.
3438
3539
```cpp
3640
class widget
@@ -52,7 +56,7 @@ void functionUsingWidget() {
5256
5357
```
5458

55-
Since C++11, there is a better way to write the previous example, by using a smart pointer from the Standard Library. The smart pointer handles the allocation and deletion of the memory it owns. This eliminates the need for an explicit destructor in the `widget` class.
59+
Since C++11, there's a better way to write the previous example: by using a smart pointer from the standard library. The smart pointer handles the allocation and deletion of the memory it owns. Using a smart pointer eliminates the need for an explicit destructor in the `widget` class.
5660

5761
```cpp
5862
#include <memory>
@@ -75,9 +79,9 @@ void functionUsingWidget() {
7579

7680
```
7781

78-
By using smart pointers for memory allocation, and handling other resources such as file handles, sockets, and so on in a similar way in your own classes, you can eliminate the potential for memory leaks. For more information, see [Smart pointers](smart-pointers-modern-cpp.md).
82+
By using smart pointers for memory allocation, you may eliminate the potential for memory leaks. This model works for other resources, such as file handles or sockets. You can manage your own resources in a similar way in your classes. For more information, see [Smart pointers](smart-pointers-modern-cpp.md).
7983

80-
C++ is designed to ensure that objects are destroyed at the correct times, that is, as blocks are exited, in reverse order of construction. When an object is destroyed, its bases and members are destroyed in a particular order. When objects are declared outside of any block, at global scope, problems can arise. When the constructor of a global object throws an exception, typically, the app faults in a way that can be difficult to debug.
84+
The design of C++ ensures objects are destroyed when they go out of scope. That is, they get destroyed as blocks are exited, in reverse order of construction. When an object is destroyed, its bases and members are destroyed in a particular order. Objects declared outside of any block, at global scope, can lead to problems. It may be difficult to debug, if the constructor of a global object throws an exception.
8185

8286
## See also
8387

docs/cpp/portability-at-abi-boundaries-modern-cpp.md

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,13 @@
11
---
2-
title: "Portability At ABI Boundaries"
2+
title: "Portability at ABI boundaries"
33
description: "Flatten C++ interfaces to C calling conventions at binary interface boundaries."
44
ms.date: "11/19/2019"
55
ms.topic: "conceptual"
66
ms.assetid: abbd405e-3038-427c-8c24-e00598f0936a
77
---
8-
# Portability At ABI Boundaries
8+
# Portability at ABI boundaries
99

10-
Use sufficiently portable types and conventions at binary interface boundaries. A “portable type” is a C built-in type or a struct that contains only C built-in types. Class types can only be used when caller and callee agree on layout, calling convention, etc. This is only possible when both are compiled with the same compiler and compiler settings.
10+
Use sufficiently portable types and conventions at binary interface boundaries. A “portable type” is a C built-in type or a struct that contains only C built-in types. Class types can only be used when caller and callee agree on layout, calling convention, etc. That's only possible when both are compiled with the same compiler and compiler settings.
1111

1212
## How to flatten a class for C portability
1313

0 commit comments

Comments
 (0)