Home | History | Annotate | Download | only in containers
      1 // Copyright 2014 The Android Open Source Project
      2 //
      3 // This software is licensed under the terms of the GNU General Public
      4 // License version 2, as published by the Free Software Foundation, and
      5 // may be copied, distributed, and modified under those terms.
      6 //
      7 // This program is distributed in the hope that it will be useful,
      8 // but WITHOUT ANY WARRANTY; without even the implied warranty of
      9 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     10 // GNU General Public License for more details.
     11 
     12 #include "android/base/containers/StringVector.h"
     13 
     14 #include "android/base/StringView.h"
     15 
     16 #include <stdio.h>
     17 
     18 namespace android {
     19 namespace base {
     20 
     21 StringVector::StringVector(const StringVector& other) : PodVector<String>() {
     22     size_t count = other.size();
     23     // We rely on the fact that an all-0 String instance is properly
     24     // initialized to the empty string.
     25     resize(count);
     26     for (size_t n = 0; n < count; ++n) {
     27         (*this) [n] = other[n];
     28     }
     29 }
     30 
     31 StringVector& StringVector::operator=(const StringVector& other) {
     32     reserve(0U);
     33     resize(other.size());
     34     for (size_t n = 0; n < other.size(); ++n) {
     35         (*this)[n] = other[n];
     36     }
     37     return *this;
     38 }
     39 
     40 StringVector::~StringVector() {
     41     reserve(0U);
     42 }
     43 
     44 void StringVector::resize(size_t newSize) {
     45     size_t oldSize = size();
     46     String* oldStrings = begin();
     47     if (newSize < oldSize) {
     48         String::finalizeSlice(oldStrings + newSize, oldSize - newSize);
     49     }
     50     PodVectorBase::resize(newSize, sizeof(String));
     51     if (oldStrings != begin()) {
     52         String::adjustMovedSlice(oldStrings, begin(), newSize);
     53     }
     54 }
     55 
     56 void StringVector::reserve(size_t newSize) {
     57     size_t oldSize = size();
     58     String* oldStrings = begin();
     59     if (newSize < oldSize) {
     60         String::finalizeSlice(oldStrings + newSize, oldSize - newSize);
     61     }
     62     PodVectorBase::reserve(newSize, sizeof(String));
     63     if (oldStrings != begin()) {
     64         String::adjustMovedSlice(oldStrings, begin(), newSize);
     65     }
     66 }
     67 
     68 void StringVector::remove(size_t index) {
     69     size_t oldSize = size();
     70     if (index >= oldSize)
     71         return;
     72     String::finalizeSlice(begin(), 1U);
     73     String::moveSlice(begin(), index + 1, index, oldSize - index);
     74 }
     75 
     76 String* StringVector::emplace(size_t index) {
     77     size_t oldSize = size();
     78     DCHECK(index <= oldSize);
     79     resize(oldSize + 1U);
     80     String::moveSlice(begin(), index, index + 1, oldSize - index);
     81     String* result = begin() + index;
     82     ::memset(result, 0, sizeof(String));
     83     return result;
     84 }
     85 
     86 void StringVector::append(const String& str) {
     87     *(this->emplace(this->size())) = str;
     88 }
     89 
     90 void StringVector::prepend(const String& str) {
     91     *(this->emplace(0U)) = str;
     92 }
     93 
     94 void StringVector::insert(size_t index, const String& str) {
     95     *(this->emplace(index)) = str;
     96 }
     97 
     98 void StringVector::append(const StringView& view) {
     99     *(this->emplace(this->size())) = view;
    100 }
    101 
    102 void StringVector::prepend(const StringView& view) {
    103     *(this->emplace(0U)) = view;
    104 }
    105 
    106 void StringVector::insert(size_t index, const StringView& view) {
    107     *(this->emplace(index)) = view;
    108 }
    109 
    110 void StringVector::swap(StringVector* other) {
    111     size_t mySize = size();
    112     size_t otherSize = other->size();
    113     PodVectorBase::swapAll(other);
    114     String::adjustMovedSlice(this->begin(), other->begin(), mySize);
    115     String::adjustMovedSlice(other->begin(), this->begin(), otherSize);
    116 }
    117 
    118 }  // namespace base
    119 }  // namespace android
    120