scoped_vector.h 4.24 KB
Newer Older
gejun's avatar
gejun committed
1 2 3 4
// Copyright (c) 2012 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

5 6
#ifndef BUTIL_MEMORY_SCOPED_VECTOR_H_
#define BUTIL_MEMORY_SCOPED_VECTOR_H_
gejun's avatar
gejun committed
7 8 9

#include <vector>

10 11 12 13
#include "butil/basictypes.h"
#include "butil/logging.h"
#include "butil/move.h"
#include "butil/stl_util.h"
gejun's avatar
gejun committed
14

15 16
namespace butil {

gejun's avatar
gejun committed
17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138
// ScopedVector wraps a vector deleting the elements from its
// destructor.
template <class T>
class ScopedVector {
  MOVE_ONLY_TYPE_FOR_CPP_03(ScopedVector, RValue)

 public:
  typedef typename std::vector<T*>::allocator_type allocator_type;
  typedef typename std::vector<T*>::size_type size_type;
  typedef typename std::vector<T*>::difference_type difference_type;
  typedef typename std::vector<T*>::pointer pointer;
  typedef typename std::vector<T*>::const_pointer const_pointer;
  typedef typename std::vector<T*>::reference reference;
  typedef typename std::vector<T*>::const_reference const_reference;
  typedef typename std::vector<T*>::value_type value_type;
  typedef typename std::vector<T*>::iterator iterator;
  typedef typename std::vector<T*>::const_iterator const_iterator;
  typedef typename std::vector<T*>::reverse_iterator reverse_iterator;
  typedef typename std::vector<T*>::const_reverse_iterator
      const_reverse_iterator;

  ScopedVector() {}
  ~ScopedVector() { clear(); }
  ScopedVector(RValue other) { swap(*other.object); }

  ScopedVector& operator=(RValue rhs) {
    swap(*rhs.object);
    return *this;
  }

  reference operator[](size_t index) { return v_[index]; }
  const_reference operator[](size_t index) const { return v_[index]; }

  bool empty() const { return v_.empty(); }
  size_t size() const { return v_.size(); }

  reverse_iterator rbegin() { return v_.rbegin(); }
  const_reverse_iterator rbegin() const { return v_.rbegin(); }
  reverse_iterator rend() { return v_.rend(); }
  const_reverse_iterator rend() const { return v_.rend(); }

  iterator begin() { return v_.begin(); }
  const_iterator begin() const { return v_.begin(); }
  iterator end() { return v_.end(); }
  const_iterator end() const { return v_.end(); }

  const_reference front() const { return v_.front(); }
  reference front() { return v_.front(); }
  const_reference back() const { return v_.back(); }
  reference back() { return v_.back(); }

  void push_back(T* elem) { v_.push_back(elem); }

  void pop_back() {
    DCHECK(!empty());
    delete v_.back();
    v_.pop_back();
  }

  std::vector<T*>& get() { return v_; }
  const std::vector<T*>& get() const { return v_; }
  void swap(std::vector<T*>& other) { v_.swap(other); }
  void swap(ScopedVector<T>& other) { v_.swap(other.v_); }
  void release(std::vector<T*>* out) {
    out->swap(v_);
    v_.clear();
  }

  void reserve(size_t capacity) { v_.reserve(capacity); }

  // Resize, deleting elements in the disappearing range if we are shrinking.
  void resize(size_t new_size) {
    if (v_.size() > new_size)
      STLDeleteContainerPointers(v_.begin() + new_size, v_.end());
    v_.resize(new_size);
  }

  template<typename InputIterator>
  void assign(InputIterator begin, InputIterator end) {
    v_.assign(begin, end);
  }

  void clear() { STLDeleteElements(&v_); }

  // Like |clear()|, but doesn't delete any elements.
  void weak_clear() { v_.clear(); }

  // Lets the ScopedVector take ownership of |x|.
  iterator insert(iterator position, T* x) {
    return v_.insert(position, x);
  }

  // Lets the ScopedVector take ownership of elements in [first,last).
  template<typename InputIterator>
  void insert(iterator position, InputIterator first, InputIterator last) {
    v_.insert(position, first, last);
  }

  iterator erase(iterator position) {
    delete *position;
    return v_.erase(position);
  }

  iterator erase(iterator first, iterator last) {
    STLDeleteContainerPointers(first, last);
    return v_.erase(first, last);
  }

  // Like |erase()|, but doesn't delete the element at |position|.
  iterator weak_erase(iterator position) {
    return v_.erase(position);
  }

  // Like |erase()|, but doesn't delete the elements in [first, last).
  iterator weak_erase(iterator first, iterator last) {
    return v_.erase(first, last);
  }

 private:
  std::vector<T*> v_;
};

139 140
} // namespace butil

141
#endif  // BUTIL_MEMORY_SCOPED_VECTOR_H_