| OLD | NEW |
| (Empty) |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | |
| 2 // Use of this source code is governed by a BSD-style license that can be | |
| 3 // found in the LICENSE file. | |
| 4 | |
| 5 #ifndef MOJO_PUBLIC_CPP_BINDINGS_STRING_H_ | |
| 6 #define MOJO_PUBLIC_CPP_BINDINGS_STRING_H_ | |
| 7 | |
| 8 #include <iosfwd> | |
| 9 #include <string> | |
| 10 | |
| 11 #include "mojo/public/cpp/bindings/lib/array_internal.h" | |
| 12 #include "mojo/public/cpp/bindings/type_converter.h" | |
| 13 #include "mojo/public/cpp/environment/logging.h" | |
| 14 | |
| 15 namespace mojo { | |
| 16 | |
| 17 // A UTF-8 encoded character string that can be null. Provides functions that | |
| 18 // are similar to std::string, along with access to the underlying std::string | |
| 19 // object. | |
| 20 class String { | |
| 21 public: | |
| 22 typedef internal::String_Data Data_; | |
| 23 | |
| 24 String() : is_null_(true) {} | |
| 25 String(const std::string& str) : value_(str), is_null_(false) {} | |
| 26 String(const char* chars) : is_null_(!chars) { | |
| 27 if (chars) | |
| 28 value_ = chars; | |
| 29 } | |
| 30 String(const char* chars, size_t num_chars) | |
| 31 : value_(chars, num_chars), is_null_(false) {} | |
| 32 String(const mojo::String& str) | |
| 33 : value_(str.value_), is_null_(str.is_null_) {} | |
| 34 | |
| 35 template <size_t N> | |
| 36 String(const char chars[N]) | |
| 37 : value_(chars, N - 1), is_null_(false) {} | |
| 38 | |
| 39 template <typename U> | |
| 40 static String From(const U& other) { | |
| 41 return TypeConverter<String, U>::Convert(other); | |
| 42 } | |
| 43 | |
| 44 template <typename U> | |
| 45 U To() const { | |
| 46 return TypeConverter<U, String>::Convert(*this); | |
| 47 } | |
| 48 | |
| 49 String& operator=(const mojo::String& str) { | |
| 50 value_ = str.value_; | |
| 51 is_null_ = str.is_null_; | |
| 52 return *this; | |
| 53 } | |
| 54 String& operator=(const std::string& str) { | |
| 55 value_ = str; | |
| 56 is_null_ = false; | |
| 57 return *this; | |
| 58 } | |
| 59 String& operator=(const char* chars) { | |
| 60 is_null_ = !chars; | |
| 61 if (chars) { | |
| 62 value_ = chars; | |
| 63 } else { | |
| 64 value_.clear(); | |
| 65 } | |
| 66 return *this; | |
| 67 } | |
| 68 | |
| 69 void reset() { | |
| 70 value_.clear(); | |
| 71 is_null_ = true; | |
| 72 } | |
| 73 | |
| 74 // Tests as true if non-null, false if null. | |
| 75 explicit operator bool() const { return !is_null_; } | |
| 76 | |
| 77 bool is_null() const { return is_null_; } | |
| 78 | |
| 79 size_t size() const { return value_.size(); } | |
| 80 | |
| 81 const char* data() const { return value_.data(); } | |
| 82 | |
| 83 const char& at(size_t offset) const { return value_.at(offset); } | |
| 84 char& at(size_t offset) { return value_.at(offset); } | |
| 85 | |
| 86 const char& operator[](size_t offset) const { return value_[offset]; } | |
| 87 char& operator[](size_t offset) { return value_[offset]; } | |
| 88 | |
| 89 const std::string& get() const { return value_; } | |
| 90 operator const std::string&() const { return value_; } | |
| 91 | |
| 92 void Swap(String* other) { | |
| 93 std::swap(is_null_, other->is_null_); | |
| 94 value_.swap(other->value_); | |
| 95 } | |
| 96 | |
| 97 void Swap(std::string* other) { | |
| 98 is_null_ = false; | |
| 99 value_.swap(*other); | |
| 100 } | |
| 101 | |
| 102 private: | |
| 103 std::string value_; | |
| 104 bool is_null_; | |
| 105 }; | |
| 106 | |
| 107 inline bool operator==(const String& a, const String& b) { | |
| 108 return a.is_null() == b.is_null() && a.get() == b.get(); | |
| 109 } | |
| 110 inline bool operator==(const char* a, const String& b) { | |
| 111 return !b.is_null() && a == b.get(); | |
| 112 } | |
| 113 inline bool operator==(const String& a, const char* b) { | |
| 114 return !a.is_null() && a.get() == b; | |
| 115 } | |
| 116 inline bool operator!=(const String& a, const String& b) { | |
| 117 return !(a == b); | |
| 118 } | |
| 119 inline bool operator!=(const char* a, const String& b) { | |
| 120 return !(a == b); | |
| 121 } | |
| 122 inline bool operator!=(const String& a, const char* b) { | |
| 123 return !(a == b); | |
| 124 } | |
| 125 | |
| 126 // TODO(jeffbrown): Decide whether this should print a sentinel value | |
| 127 // such as "<null>" when formatting null strings. | |
| 128 inline std::ostream& operator<<(std::ostream& out, const String& s) { | |
| 129 return out << s.get(); | |
| 130 } | |
| 131 | |
| 132 inline bool operator<(const String& a, const String& b) { | |
| 133 if (a.is_null()) | |
| 134 return !b.is_null(); | |
| 135 if (b.is_null()) | |
| 136 return false; | |
| 137 | |
| 138 return a.get() < b.get(); | |
| 139 } | |
| 140 | |
| 141 // TODO(darin): Add similar variants of operator<,<=,>,>= | |
| 142 | |
| 143 template <> | |
| 144 struct TypeConverter<String, std::string> { | |
| 145 static String Convert(const std::string& input) { return String(input); } | |
| 146 }; | |
| 147 | |
| 148 template <> | |
| 149 struct TypeConverter<std::string, String> { | |
| 150 static std::string Convert(const String& input) { return input; } | |
| 151 }; | |
| 152 | |
| 153 template <size_t N> | |
| 154 struct TypeConverter<String, char[N]> { | |
| 155 static String Convert(const char input[N]) { | |
| 156 MOJO_DCHECK(input); | |
| 157 return String(input, N - 1); | |
| 158 } | |
| 159 }; | |
| 160 | |
| 161 // Appease MSVC. | |
| 162 template <size_t N> | |
| 163 struct TypeConverter<String, const char[N]> { | |
| 164 static String Convert(const char input[N]) { | |
| 165 MOJO_DCHECK(input); | |
| 166 return String(input, N - 1); | |
| 167 } | |
| 168 }; | |
| 169 | |
| 170 template <> | |
| 171 struct TypeConverter<String, const char*> { | |
| 172 // |input| may be null, in which case a null String will be returned. | |
| 173 static String Convert(const char* input) { return String(input); } | |
| 174 }; | |
| 175 | |
| 176 } // namespace mojo | |
| 177 | |
| 178 #endif // MOJO_PUBLIC_CPP_BINDINGS_STRING_H_ | |
| OLD | NEW |