OLD | NEW |
---|---|
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 // Scopers help you manage ownership of a pointer, helping you easily manage a | 5 // Scopers help you manage ownership of a pointer, helping you easily manage a |
6 // pointer within a scope, and automatically destroying the pointer at the end | 6 // pointer within a scope, and automatically destroying the pointer at the end |
7 // of a scope. There are two main classes you will use, which correspond to the | 7 // of a scope. There are two main classes you will use, which correspond to the |
8 // operators new/delete and new[]/delete[]. | 8 // operators new/delete and new[]/delete[]. |
9 // | 9 // |
10 // Example usage (scoped_ptr<T>): | 10 // Example usage (scoped_ptr<T>): |
(...skipping 295 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
306 template <class T, class D = base::DefaultDeleter<T> > | 306 template <class T, class D = base::DefaultDeleter<T> > |
307 class scoped_ptr { | 307 class scoped_ptr { |
308 MOVE_ONLY_TYPE_WITH_MOVE_CONSTRUCTOR_FOR_CPP_03(scoped_ptr) | 308 MOVE_ONLY_TYPE_WITH_MOVE_CONSTRUCTOR_FOR_CPP_03(scoped_ptr) |
309 | 309 |
310 COMPILE_ASSERT(base::internal::IsNotRefCounted<T>::value, | 310 COMPILE_ASSERT(base::internal::IsNotRefCounted<T>::value, |
311 T_is_refcounted_type_and_needs_scoped_refptr); | 311 T_is_refcounted_type_and_needs_scoped_refptr); |
312 | 312 |
313 public: | 313 public: |
314 // The element and deleter types. | 314 // The element and deleter types. |
315 typedef T element_type; | 315 typedef T element_type; |
316 using Pointer = element_type*; | |
316 typedef D deleter_type; | 317 typedef D deleter_type; |
317 | 318 |
318 // Constructor. Defaults to initializing with nullptr. | 319 // Constructor. Defaults to initializing with nullptr. |
319 scoped_ptr() : impl_(nullptr) {} | 320 scoped_ptr() : impl_(nullptr) {} |
320 | 321 |
321 // Constructor. Takes ownership of p. | 322 // Constructor. Takes ownership of p. |
322 explicit scoped_ptr(element_type* p) : impl_(p) {} | 323 explicit scoped_ptr(element_type* p) : impl_(p) {} |
323 | 324 |
324 // Constructor. Allows initialization of a stateful deleter. | 325 // Constructor. Allows initialization of a stateful deleter. |
325 scoped_ptr(element_type* p, const D& d) : impl_(p, d) {} | 326 scoped_ptr(element_type* p, const D& d) : impl_(p, d) {} |
326 | 327 |
327 // Constructor. Allows construction from a nullptr. | 328 // Constructor. Allows construction from a nullptr. |
328 scoped_ptr(std::nullptr_t) : impl_(nullptr) {} | 329 scoped_ptr(std::nullptr_t) : impl_(nullptr) {} |
329 | 330 |
331 // Move constructor. | |
332 scoped_ptr(scoped_ptr&& other) : impl_(&other.impl_) {} | |
333 | |
330 // Constructor. Allows construction from a scoped_ptr rvalue for a | 334 // Constructor. Allows construction from a scoped_ptr rvalue for a |
331 // convertible type and deleter. | 335 // convertible type and deleter. |
332 // | |
333 // IMPLEMENTATION NOTE: C++11 unique_ptr<> keeps this constructor distinct | |
334 // from the normal move constructor. By C++11 20.7.1.2.1.21, this constructor | |
335 // has different post-conditions if D is a reference type. Since this | |
336 // implementation does not support deleters with reference type, | |
337 // we do not need a separate move constructor allowing us to avoid one | |
338 // use of SFINAE. You only need to care about this if you modify the | |
339 // implementation of scoped_ptr. | |
340 template <typename U, typename V> | 336 template <typename U, typename V> |
341 scoped_ptr(scoped_ptr<U, V>&& other) | 337 scoped_ptr(scoped_ptr<U, V>&& other, |
danakj
2015/11/18 23:39:34
I wish clang-format did a better job wrapping temp
| |
338 typename std::enable_if< | |
339 std::is_convertible<typename scoped_ptr<U, V>::Pointer, | |
danakj
2015/11/18 23:39:34
Can you explain to me why you used enable_if here?
dcheng
2015/11/19 00:23:24
I don't actually know the reasoning behind this: i
vmpstr
2015/11/19 00:37:18
Is it possible to enable_if in the template list i
dcheng
2015/11/19 00:38:57
Any particular reason to prefer that? I guess the
| |
340 Pointer>::value>::type* = nullptr) | |
342 : impl_(&other.impl_) { | 341 : impl_(&other.impl_) { |
343 COMPILE_ASSERT(!base::is_array<U>::value, U_cannot_be_an_array); | 342 COMPILE_ASSERT(!base::is_array<U>::value, U_cannot_be_an_array); |
344 } | 343 } |
345 | 344 |
346 // operator=. Allows assignment from a scoped_ptr rvalue for a convertible | 345 // operator=. Allows assignment from a scoped_ptr rvalue for a convertible |
347 // type and deleter. | 346 // type and deleter. |
348 // | 347 // |
349 // IMPLEMENTATION NOTE: C++11 unique_ptr<> keeps this operator= distinct from | 348 // IMPLEMENTATION NOTE: C++11 unique_ptr<> keeps this operator= distinct from |
350 // the normal move assignment operator. By C++11 20.7.1.2.3.4, this templated | 349 // the normal move assignment operator. By C++11 20.7.1.2.3.4, this templated |
351 // form has different requirements on for move-only Deleters. Since this | 350 // form has different requirements on for move-only Deleters. Since this |
(...skipping 268 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
620 scoped_ptr<T> make_scoped_ptr(T* ptr) { | 619 scoped_ptr<T> make_scoped_ptr(T* ptr) { |
621 return scoped_ptr<T>(ptr); | 620 return scoped_ptr<T>(ptr); |
622 } | 621 } |
623 | 622 |
624 template <typename T> | 623 template <typename T> |
625 std::ostream& operator<<(std::ostream& out, const scoped_ptr<T>& p) { | 624 std::ostream& operator<<(std::ostream& out, const scoped_ptr<T>& p) { |
626 return out << p.get(); | 625 return out << p.get(); |
627 } | 626 } |
628 | 627 |
629 #endif // BASE_MEMORY_SCOPED_PTR_H_ | 628 #endif // BASE_MEMORY_SCOPED_PTR_H_ |
OLD | NEW |