Skip to content

Commit 7ecc4fc

Browse files
authored
Merge pull request #2477 from mikeblome/mb-pointers
Update and improve pointers topic
2 parents 77d42c3 + d8949af commit 7ecc4fc

11 files changed

+449
-324
lines changed

docs/cpp/const-and-volatile-pointers.md

+6-5
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,12 @@
11
---
2-
title: "const and volatile Pointers"
3-
ms.date: "11/04/2016"
2+
title: "const and volatile pointers"
3+
ms.date: "11/19/2019"
44
helpviewer_keywords: ["volatile keyword [C++], and pointers", "pointers, and const", "pointers, and volatile", "const keyword [C++], volatile pointers"]
55
ms.assetid: 0c92dc6c-400e-4342-b345-63ddfe649d7e
66
---
7-
# const and volatile Pointers
7+
# const and volatile pointers
88

9-
The [const](../cpp/const-cpp.md) and [volatile](../cpp/volatile-cpp.md) keywords change how pointers are treated. The **const** keyword specifies that the pointer cannot be modified after initialization; the pointer is protected from modification thereafter.
9+
The [const](const-cpp.md) and [volatile](volatile-cpp.md) keywords change how pointers are treated. The **const** keyword specifies that the pointer cannot be modified after initialization; the pointer is protected from modification thereafter.
1010

1111
The **volatile** keyword specifies that the value associated with the name that follows can be modified by actions other than those in the user application. Therefore, the **volatile** keyword is useful for declaring objects in shared memory that can be accessed by multiple processes or global data areas used for communication with interrupt service routines.
1212

@@ -116,4 +116,5 @@ int main() {
116116
117117
## See also
118118
119-
[Pointers](../cpp/pointers-cpp.md)
119+
[Pointers](pointers-cpp.md)
120+
[Raw pointers](raw-pointers.md)

docs/cpp/how-to-create-and-use-ccomptr-and-ccomqiptr-instances.md

+3-3
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,11 @@
11
---
2-
title: "How to: Create and Use CComPtr and CComQIPtr Instances"
2+
title: "How to: Create and use CComPtr and CComQIPtr instances"
33
ms.custom: "how-to"
4-
ms.date: "11/04/2016"
4+
ms.date: "11/19/2019"
55
ms.topic: "conceptual"
66
ms.assetid: b0356cfb-12cc-4ee8-b988-8311ed1ab5e0
77
---
8-
# How to: Create and Use CComPtr and CComQIPtr Instances
8+
# How to: Create and use CComPtr and CComQIPtr instances
99

1010
In classic Windows programming, libraries are often implemented as COM objects (or more precisely, as COM servers). Many Windows operating system components are implemented as COM servers, and many contributors provide libraries in this form. For information about the basics of COM, see [Component Object Model (COM)](/windows/win32/com/component-object-model--com--portal).
1111

docs/cpp/how-to-create-and-use-shared-ptr-instances.md

+10-10
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,17 @@
11
---
2-
title: "How to: Create and Use shared_ptr Instances"
2+
title: "How to: Create and use shared_ptr instances"
33
ms.custom: "how-to"
4-
ms.date: "05/22/2019"
4+
ms.date: "11/19/2019"
55
ms.topic: "conceptual"
66
ms.assetid: 7d6ebb73-fa0d-4b0b-a528-bf05de96518e
77
---
8-
# How to: Create and Use shared_ptr Instances
8+
# How to: Create and Use shared_ptr instances
99

1010
The `shared_ptr` type is a smart pointer in the C++ standard library that is designed for scenarios in which more than one owner might have to manage the lifetime of the object in memory. After you initialize a `shared_ptr` you can copy it, pass it by value in function arguments, and assign it to other `shared_ptr` instances. All the instances point to the same object, and share access to one "control block" that increments and decrements the reference count whenever a new `shared_ptr` is added, goes out of scope, or is reset. When the reference count reaches zero, the control block deletes the memory resource and itself.
1111

1212
The following illustration shows several `shared_ptr` instances that point to one memory location.
1313

14-
![Shared pointer diagram](../cpp/media/shared_ptr.png "Shared pointer diagram")
14+
![Shared pointer diagram](media/shared_ptr.png "Shared pointer diagram")
1515

1616
## Example setup
1717

@@ -68,25 +68,25 @@ int main()
6868
6969
Whenever possible, use the [make_shared](../standard-library/memory-functions.md#make_shared) function to create a `shared_ptr` when the memory resource is created for the first time. `make_shared` is exception-safe. It uses the same call to allocate the memory for the control block and the resource, which reduces the construction overhead. If you don't use `make_shared`, then you have to use an explicit `new` expression to create the object before you pass it to the `shared_ptr` constructor. The following example shows various ways to declare and initialize a `shared_ptr` together with a new object.
7070
71-
[!code-cpp[stl_smart_pointers#1](../cpp/codesnippet/CPP/how-to-create-and-use-shared-ptr-instances_1.cpp)]
71+
[!code-cpp[stl_smart_pointers#1](codesnippet/CPP/how-to-create-and-use-shared-ptr-instances_1.cpp)]
7272
7373
## Example 2
7474
7575
The following example shows how to declare and initialize `shared_ptr` instances that take on shared ownership of an object that has already been allocated by another `shared_ptr`. Assume that `sp2` is an initialized `shared_ptr`.
7676
77-
[!code-cpp[stl_smart_pointers#2](../cpp/codesnippet/CPP/how-to-create-and-use-shared-ptr-instances_2.cpp)]
77+
[!code-cpp[stl_smart_pointers#2](codesnippet/CPP/how-to-create-and-use-shared-ptr-instances_2.cpp)]
7878
7979
## Example 3
8080
8181
`shared_ptr` is also helpful in C++ Standard Library containers when you're using algorithms that copy elements. You can wrap elements in a `shared_ptr`, and then copy it into other containers with the understanding that the underlying memory is valid as long as you need it, and no longer. The following example shows how to use the `remove_copy_if` algorithm on `shared_ptr` instances in a vector.
8282
83-
[!code-cpp[stl_smart_pointers#4](../cpp/codesnippet/CPP/how-to-create-and-use-shared-ptr-instances_3.cpp)]
83+
[!code-cpp[stl_smart_pointers#4](codesnippet/CPP/how-to-create-and-use-shared-ptr-instances_3.cpp)]
8484
8585
## Example 4
8686
8787
You can use `dynamic_pointer_cast`, `static_pointer_cast`, and `const_pointer_cast` to cast a `shared_ptr`. These functions resemble the `dynamic_cast`, `static_cast`, and `const_cast` operators. The following example shows how to test the derived type of each element in a vector of `shared_ptr` of base classes, and then copy the elements and display information about them.
8888
89-
[!code-cpp[stl_smart_pointers#5](../cpp/codesnippet/CPP/how-to-create-and-use-shared-ptr-instances_4.cpp)]
89+
[!code-cpp[stl_smart_pointers#5](codesnippet/CPP/how-to-create-and-use-shared-ptr-instances_4.cpp)]
9090
9191
## Example 5
9292
@@ -108,8 +108,8 @@ You can pass a `shared_ptr` to another function in the following ways:
108108
109109
The following example shows how `shared_ptr` overloads various comparison operators to enable pointer comparisons on the memory that is owned by the `shared_ptr` instances.
110110
111-
[!code-cpp[stl_smart_pointers#3](../cpp/codesnippet/CPP/how-to-create-and-use-shared-ptr-instances_6.cpp)]
111+
[!code-cpp[stl_smart_pointers#3](codesnippet/CPP/how-to-create-and-use-shared-ptr-instances_6.cpp)]
112112
113113
## See also
114114
115-
[Smart Pointers (Modern C++)](../cpp/smart-pointers-modern-cpp.md)
115+
[Smart Pointers (Modern C++)](smart-pointers-modern-cpp.md)
Original file line numberDiff line numberDiff line change
@@ -1,51 +1,51 @@
11
---
2-
title: "How to: Create and Use unique_ptr Instances"
2+
title: "How to: Create and use unique_ptr instances"
33
ms.custom: "how-to"
44
ms.date: "11/19/2018"
55
ms.topic: "conceptual"
66
ms.assetid: 9a373030-e587-452f-b9a5-c5f9d58b7673
77
---
8-
# How to: Create and Use unique_ptr Instances
8+
# How to: Create and use unique_ptr instances
99

1010
A [unique_ptr](../standard-library/unique-ptr-class.md) does not share its pointer. It cannot be copied to another `unique_ptr`, passed by value to a function, or used in any C++ Standard Library algorithm that requires copies to be made. A `unique_ptr` can only be moved. This means that the ownership of the memory resource is transferred to another `unique_ptr` and the original `unique_ptr` no longer owns it. We recommend that you restrict an object to one owner, because multiple ownership adds complexity to the program logic. Therefore, when you need a smart pointer for a plain C++ object, use `unique_ptr`, and when you construct a `unique_ptr`, use the [make_unique](../standard-library/memory-functions.md#make_unique) helper function.
1111

1212
The following diagram illustrates the transfer of ownership between two `unique_ptr` instances.
1313

14-
![Moving the ownership of a unique_ptr](../cpp/media/unique_ptr.png "Moving the ownership of a unique_ptr")
14+
![Moving the ownership of a unique_ptr](media/unique_ptr.png "Moving the ownership of a unique_ptr")
1515

1616
`unique_ptr` is defined in the `<memory>` header in the C++ Standard Library. It is exactly as efficient as a raw pointer and can be used in C++ Standard Library containers. The addition of `unique_ptr` instances to C++ Standard Library containers is efficient because the move constructor of the `unique_ptr` eliminates the need for a copy operation.
1717

18-
## Example
18+
## Example 1
1919

2020
The following example shows how to create `unique_ptr` instances and pass them between functions.
2121

22-
[!code-cpp[stl_smart_pointers#210](../cpp/codesnippet/CPP/how-to-create-and-use-unique-ptr-instances_1.cpp)]
22+
[!code-cpp[stl_smart_pointers#210](codesnippet/CPP/how-to-create-and-use-unique-ptr-instances_1.cpp)]
2323

2424
These examples demonstrate this basic characteristic of `unique_ptr`: it can be moved, but not copied. "Moving" transfers ownership to a new `unique_ptr` and resets the old `unique_ptr`.
2525

26-
## Example
26+
## Example 2
2727

2828
The following example shows how to create `unique_ptr` instances and use them in a vector.
2929

30-
[!code-cpp[stl_smart_pointers#211](../cpp/codesnippet/CPP/how-to-create-and-use-unique-ptr-instances_2.cpp)]
30+
[!code-cpp[stl_smart_pointers#211](codesnippet/CPP/how-to-create-and-use-unique-ptr-instances_2.cpp)]
3131

3232
In the range for loop, notice that the `unique_ptr` is passed by reference. If you try to pass by value here, the compiler will throw an error because the `unique_ptr` copy constructor is deleted.
3333

34-
## Example
34+
## Example 3
3535

3636
The following example shows how to initialize a `unique_ptr` that is a class member.
3737

38-
[!code-cpp[stl_smart_pointers#212](../cpp/codesnippet/CPP/how-to-create-and-use-unique-ptr-instances_3.cpp)]
38+
[!code-cpp[stl_smart_pointers#212](codesnippet/CPP/how-to-create-and-use-unique-ptr-instances_3.cpp)]
3939

40-
## Example
40+
## Example 4
4141

4242
You can use [make_unique](../standard-library/memory-functions.md#make_unique) to create a `unique_ptr` to an array, but you cannot use `make_unique` to initialize the array elements.
4343

44-
[!code-cpp[stl_smart_pointers#213](../cpp/codesnippet/CPP/how-to-create-and-use-unique-ptr-instances_4.cpp)]
44+
[!code-cpp[stl_smart_pointers#213](codesnippet/CPP/how-to-create-and-use-unique-ptr-instances_4.cpp)]
4545

4646
For more examples, see [make_unique](../standard-library/memory-functions.md#make_unique).
4747

4848
## See also
4949

50-
[Smart Pointers (Modern C++)](../cpp/smart-pointers-modern-cpp.md)<br/>
50+
[Smart Pointers (Modern C++)](smart-pointers-modern-cpp.md)<br/>
5151
[make_unique](../standard-library/memory-functions.md#make_unique)

docs/cpp/how-to-create-and-use-weak-ptr-instances.md

+5-5
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,15 @@
11
---
2-
title: "How to: Create and Use weak_ptr Instances"
2+
title: "How to: Create and use weak_ptr instances"
33
ms.custom: "how-to"
4-
ms.date: "09/18/2019"
4+
ms.date: "11/19/2019"
55
ms.topic: "conceptual"
66
ms.assetid: 8dd6909b-b070-4afa-9696-f2fc94579c65
77
---
8-
# How to: Create and Use weak_ptr Instances
8+
# How to: Create and use weak_ptr instances
99

10-
Sometimes an object must store a way to access the underlying object of a `shared_ptr` without causing the reference count to be incremented. Typically, this situation occurs when you have cyclic references between `shared_ptr` instances.
10+
Sometimes an object must store a way to access the underlying object of a [shared_ptr](../standard-library/shared-ptr-class.md) without causing the reference count to be incremented. Typically, this situation occurs when you have cyclic references between `shared_ptr` instances.
1111

12-
The best design is to avoid shared ownership of pointers whenever you can. However, if you must have shared ownership of `shared_ptr` instances, avoid cyclic references between them. When cyclic references are unavoidable, or even preferable for some reason, use `weak_ptr` to give one or more of the owners a weak reference to another `shared_ptr`. By using a `weak_ptr`, you can create a `shared_ptr` that joins to an existing set of related instances, but only if the underlying memory resource is still valid. A `weak_ptr` itself does not participate in the reference counting, and therefore, it cannot prevent the reference count from going to zero. However, you can use a `weak_ptr` to try to obtain a new copy of the `shared_ptr` with which it was initialized. If the memory has already been deleted, the `weak_ptr`'s bool operator returns `false`. If the memory is still valid, the new shared pointer increments the reference count and guarantees that the memory will be valid as long as the `shared_ptr` variable stays in scope.
12+
The best design is to avoid shared ownership of pointers whenever you can. However, if you must have shared ownership of `shared_ptr` instances, avoid cyclic references between them. When cyclic references are unavoidable, or even preferable for some reason, use [weak_ptr](../standard-library/weak-ptr-class.md) to give one or more of the owners a weak reference to another `shared_ptr`. By using a `weak_ptr`, you can create a `shared_ptr` that joins to an existing set of related instances, but only if the underlying memory resource is still valid. A `weak_ptr` itself does not participate in the reference counting, and therefore, it cannot prevent the reference count from going to zero. However, you can use a `weak_ptr` to try to obtain a new copy of the `shared_ptr` with which it was initialized. If the memory has already been deleted, the `weak_ptr`'s bool operator returns `false`. If the memory is still valid, the new shared pointer increments the reference count and guarantees that the memory will be valid as long as the `shared_ptr` variable stays in scope.
1313

1414
## Example
1515

docs/cpp/new-and-delete-operators.md

+10-17
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,13 @@
11
---
22
title: "new and delete Operators"
3-
ms.date: "05/07/2019"
3+
ms.date: "11/19/2019"
44
f1_keywords: ["delete_cpp", "new"]
55
helpviewer_keywords: ["new keyword [C++]", "delete keyword [C++]"]
66
ms.assetid: fa721b9e-0374-4f04-bb87-032ea775bcc8
77
---
8-
# new and delete Operators
8+
# new and delete operators
99

10-
C++ supports dynamic allocation and deallocation of objects using the [new](../cpp/new-operator-cpp.md) and [delete](../cpp/delete-operator-cpp.md) operators. These operators allocate memory for objects from a pool called the free store. The **new** operator calls the special function [operator new](../cpp/new-operator-cpp.md), and the **delete** operator calls the special function [operator delete](../cpp/delete-operator-cpp.md).
10+
C++ supports dynamic allocation and deallocation of objects using the [new](new-operator-cpp.md) and [delete](delete-operator-cpp.md) operators. These operators allocate memory for objects from a pool called the free store. The **new** operator calls the special function [operator new](new-operator-cpp.md), and the **delete** operator calls the special function [operator delete](delete-operator-cpp.md).
1111

1212
The **new** function in the C++ Standard Library supports the behavior specified in the C++ standard, which is to throw a std::bad_alloc exception if the memory allocation fails. If you still want the non-throwing version of **new**, link your program with nothrownew.obj. However, when you link with nothrownew.obj, the default **operator new** in the C++ Standard Library no longer functions.
1313

@@ -21,13 +21,13 @@ When a statement such as the following is encountered in a program, it translate
2121
char *pch = new char[BUFFER_SIZE];
2222
```
2323

24-
If the request is for zero bytes of storage, **operator new** returns a pointer to a distinct object (that is, repeated calls to **operator new** return different pointers). If there is insufficient memory for the allocation request, **operator new** throws a std::bad_alloc exception, or returns **nullptr** if you have linked in non-throwing **operator new** support.
24+
If the request is for zero bytes of storage, **operator new** returns a pointer to a distinct object (that is, repeated calls to **operator new** return different pointers). If there is insufficient memory for the allocation request, **operator new** throws a `std::bad_alloc` exception, or returns **nullptr** if you have linked in non-throwing **operator new** support.
2525

2626
You can write a routine that attempts to free memory and retry the allocation; see [_set_new_handler](../c-runtime-library/reference/set-new-handler.md) for more information. For more details on the recovery scheme, see the Handling insufficient memory section of this topic.
2727

2828
The two scopes for **operator new** functions are described in the following table.
2929

30-
### Scope for operator new Functions
30+
### Scope for operator new functions
3131

3232
|Operator|Scope|
3333
|--------------|-----------|
@@ -41,7 +41,6 @@ The global **operator new** function is called when the **new** operator is used
4141
An **operator new** function defined for a class is a static member function (which cannot, therefore, be virtual) that hides the global **operator new** function for objects of that class type. Consider the case where **new** is used to allocate and set memory to a given value:
4242

4343
```cpp
44-
// spec1_the_operator_new_function1.cpp
4544
#include <malloc.h>
4645
#include <memory.h>
4746

@@ -77,7 +76,6 @@ Blanks *SomeBlanks = new Blanks;
7776
The compiler supports member array **new** and **delete** operators in a class declaration. For example:
7877

7978
```cpp
80-
// spec1_the_operator_new_function2.cpp
8179
class MyClass
8280
{
8381
public:
@@ -99,11 +97,9 @@ int main()
9997

10098
### Handling insufficient memory
10199

102-
Testing for failed memory allocation can be done with code such as the following:
100+
Testing for failed memory allocation can be done as shown here:
103101

104102
```cpp
105-
// insufficient_memory_conditions.cpp
106-
// compile with: /EHsc
107103
#include <iostream>
108104
using namespace std;
109105
#define BIG_NUMBER 100000000
@@ -116,7 +112,7 @@ int main() {
116112
}
117113
```
118114
119-
There is another ways to handle failed memory allocation requests: write a custom recovery routine to handle such a failure, then register your function by calling the [_set_new_handler](../c-runtime-library/reference/set-new-handler.md) run-time function.
115+
There is another way to handle failed memory allocation requests. Write a custom recovery routine to handle such a failure, then register your function by calling the [_set_new_handler](../c-runtime-library/reference/set-new-handler.md) run-time function.
120116
121117
## <a id="delete_operator"> </a> The delete operator
122118
@@ -133,16 +129,13 @@ void operator delete( void *, size_t );
133129

134130
Only one of the preceding two forms can be present for a given class. The first form takes a single argument of type `void *`, which contains a pointer to the object to deallocate. The second form—sized deallocation—takes two arguments, the first of which is a pointer to the memory block to deallocate and the second of which is the number of bytes to deallocate. The return type of both forms is **void** (**operator delete** cannot return a value).
135131

136-
The intent of the second form is to speed up searching for the correct size category of the object to be deleted, which is often not stored near the allocation itself and likely uncached; the second form is particularly useful when an **operator delete** function from a base class is used to delete an object of a derived class.
132+
The intent of the second form is to speed up searching for the correct size category of the object to be deleted, which is often not stored near the allocation itself and likely uncached. The second form is useful when an **operator delete** function from a base class is used to delete an object of a derived class.
137133

138-
The **operator delete** function is static; therefore, it cannot be virtual. The **operator delete** function obeys access control, as described in [Member-Access Control](../cpp/member-access-control-cpp.md).
134+
The **operator delete** function is static; therefore, it cannot be virtual. The **operator delete** function obeys access control, as described in [Member-Access Control](member-access-control-cpp.md).
139135

140136
The following example shows user-defined **operator new** and **operator delete** functions designed to log allocations and deallocations of memory:
141137

142138
```cpp
143-
// spec1_the_operator_delete_function1.cpp
144-
// compile with: /EHsc
145-
// arguments: 3
146139
#include <iostream>
147140
using namespace std;
148141

@@ -207,4 +200,4 @@ void f() {
207200
X *pX = new X[5];
208201
delete [] pX;
209202
}
210-
```
203+
```

0 commit comments

Comments
 (0)