Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(52)

Side by Side Diff: base/values.cc

Issue 2740373002: Cleaning up base::Value assignment. (Closed)
Patch Set: Rebase. Created 3 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « base/values.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 #include "base/values.h" 5 #include "base/values.h"
6 6
7 #include <string.h> 7 #include <string.h>
8 8
9 #include <algorithm> 9 #include <algorithm>
10 #include <cmath> 10 #include <cmath>
(...skipping 155 matching lines...) Expand 10 before | Expand all | Expand 10 after
166 166
167 Value::Value(const std::vector<char>& in_blob) : type_(Type::BINARY) { 167 Value::Value(const std::vector<char>& in_blob) : type_(Type::BINARY) {
168 binary_value_.Init(in_blob); 168 binary_value_.Init(in_blob);
169 } 169 }
170 170
171 Value::Value(std::vector<char>&& in_blob) : type_(Type::BINARY) { 171 Value::Value(std::vector<char>&& in_blob) : type_(Type::BINARY) {
172 binary_value_.Init(std::move(in_blob)); 172 binary_value_.Init(std::move(in_blob));
173 } 173 }
174 174
175 Value& Value::operator=(const Value& that) { 175 Value& Value::operator=(const Value& that) {
176 if (this != &that) { 176 if (type_ == that.type_) {
177 if (type_ == that.type_) { 177 InternalCopyAssignFromSameType(that);
178 InternalCopyAssignFromSameType(that); 178 } else {
179 } else { 179 // This is not a self assignment because the type_ doesn't match.
180 InternalCleanup(); 180 InternalCleanup();
181 InternalCopyConstructFrom(that); 181 InternalCopyConstructFrom(that);
182 }
183 } 182 }
184 183
185 return *this; 184 return *this;
186 } 185 }
187 186
188 Value& Value::operator=(Value&& that) { 187 Value& Value::operator=(Value&& that) {
189 if (this != &that) { 188 DCHECK(this != &that) << "attempt to self move assign.";
190 if (type_ == that.type_) { 189 InternalCleanup();
191 InternalMoveAssignFromSameType(std::move(that)); 190 InternalMoveConstructFrom(std::move(that));
192 } else {
193 InternalCleanup();
194 InternalMoveConstructFrom(std::move(that));
195 }
196 }
197 191
198 return *this; 192 return *this;
199 } 193 }
200 194
201 Value::~Value() { 195 Value::~Value() {
202 InternalCleanup(); 196 InternalCleanup();
203 alive_ = false; 197 alive_ = false;
204 } 198 }
205 199
206 // static 200 // static
(...skipping 320 matching lines...) Expand 10 before | Expand all | Expand 10 after
527 case Type::DICTIONARY: 521 case Type::DICTIONARY:
528 dict_ptr_.InitFromMove(std::move(that.dict_ptr_)); 522 dict_ptr_.InitFromMove(std::move(that.dict_ptr_));
529 return; 523 return;
530 case Type::LIST: 524 case Type::LIST:
531 list_.InitFromMove(std::move(that.list_)); 525 list_.InitFromMove(std::move(that.list_));
532 return; 526 return;
533 } 527 }
534 } 528 }
535 529
536 void Value::InternalCopyAssignFromSameType(const Value& that) { 530 void Value::InternalCopyAssignFromSameType(const Value& that) {
531 // TODO(crbug.com/646113): make this a DCHECK once base::Value does not have
532 // subclasses.
537 CHECK_EQ(type_, that.type_); 533 CHECK_EQ(type_, that.type_);
538 534
539 switch (type_) { 535 switch (type_) {
540 case Type::NONE: 536 case Type::NONE:
541 case Type::BOOLEAN: 537 case Type::BOOLEAN:
542 case Type::INTEGER: 538 case Type::INTEGER:
543 case Type::DOUBLE: 539 case Type::DOUBLE:
544 InternalCopyFundamentalValue(that); 540 InternalCopyFundamentalValue(that);
545 return; 541 return;
546 542
547 case Type::STRING: 543 case Type::STRING:
548 *string_value_ = *that.string_value_; 544 *string_value_ = *that.string_value_;
549 return; 545 return;
550 case Type::BINARY: 546 case Type::BINARY:
551 *binary_value_ = *that.binary_value_; 547 *binary_value_ = *that.binary_value_;
552 return; 548 return;
553 // DictStorage and ListStorage are move-only types due to the presence of 549 // DictStorage and ListStorage are move-only types due to the presence of
554 // unique_ptrs. This is why the call to |CreateDeepCopy| is necessary here. 550 // unique_ptrs. This is why the call to |CreateDeepCopy| is necessary here.
555 // TODO(crbug.com/646113): Clean this up when DictStorage and ListStorage 551 // TODO(crbug.com/646113): Clean this up when DictStorage and ListStorage
556 // can be copied directly. 552 // can be copied directly.
557 case Type::DICTIONARY: 553 case Type::DICTIONARY:
558 *dict_ptr_ = std::move(*that.CreateDeepCopy()->dict_ptr_); 554 *dict_ptr_ = std::move(*that.CreateDeepCopy()->dict_ptr_);
559 return; 555 return;
560 case Type::LIST: 556 case Type::LIST:
561 *list_ = std::move(*that.CreateDeepCopy()->list_); 557 *list_ = std::move(*that.CreateDeepCopy()->list_);
562 return; 558 return;
563 } 559 }
564 } 560 }
565 561
566 void Value::InternalMoveAssignFromSameType(Value&& that) {
567 CHECK_EQ(type_, that.type_);
568
569 switch (type_) {
570 case Type::NONE:
571 case Type::BOOLEAN:
572 case Type::INTEGER:
573 case Type::DOUBLE:
574 InternalCopyFundamentalValue(that);
575 return;
576
577 case Type::STRING:
578 *string_value_ = std::move(*that.string_value_);
579 return;
580 case Type::BINARY:
581 *binary_value_ = std::move(*that.binary_value_);
582 return;
583 case Type::DICTIONARY:
584 *dict_ptr_ = std::move(*that.dict_ptr_);
585 return;
586 case Type::LIST:
587 *list_ = std::move(*that.list_);
588 return;
589 }
590 }
591
592 void Value::InternalCleanup() { 562 void Value::InternalCleanup() {
593 CHECK(alive_); 563 CHECK(alive_);
594 564
595 switch (type_) { 565 switch (type_) {
596 case Type::NONE: 566 case Type::NONE:
597 case Type::BOOLEAN: 567 case Type::BOOLEAN:
598 case Type::INTEGER: 568 case Type::INTEGER:
599 case Type::DOUBLE: 569 case Type::DOUBLE:
600 // Nothing to do 570 // Nothing to do
601 return; 571 return;
(...skipping 756 matching lines...) Expand 10 before | Expand all | Expand 10 after
1358 } 1328 }
1359 1329
1360 std::ostream& operator<<(std::ostream& out, const Value::Type& type) { 1330 std::ostream& operator<<(std::ostream& out, const Value::Type& type) {
1361 if (static_cast<int>(type) < 0 || 1331 if (static_cast<int>(type) < 0 ||
1362 static_cast<size_t>(type) >= arraysize(kTypeNames)) 1332 static_cast<size_t>(type) >= arraysize(kTypeNames))
1363 return out << "Invalid Type (index = " << static_cast<int>(type) << ")"; 1333 return out << "Invalid Type (index = " << static_cast<int>(type) << ")";
1364 return out << Value::GetTypeName(type); 1334 return out << Value::GetTypeName(type);
1365 } 1335 }
1366 1336
1367 } // namespace base 1337 } // namespace base
OLDNEW
« no previous file with comments | « base/values.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698