diff options
Diffstat (limited to 'chromeos/strings')
-rw-r--r-- | chromeos/strings/string_utils.cc | 99 | ||||
-rw-r--r-- | chromeos/strings/string_utils.h | 56 | ||||
-rw-r--r-- | chromeos/strings/string_utils_unittest.cc | 111 |
3 files changed, 266 insertions, 0 deletions
diff --git a/chromeos/strings/string_utils.cc b/chromeos/strings/string_utils.cc new file mode 100644 index 0000000..fa7aba3 --- /dev/null +++ b/chromeos/strings/string_utils.cc @@ -0,0 +1,99 @@ +// Copyright 2014 The Chromium OS Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include <chromeos/strings/string_utils.h> + +#include <algorithm> +#include <string.h> +#include <utility> + +#include <base/strings/string_util.h> +#include <base/strings/stringprintf.h> + +namespace chromeos { +namespace string_utils { + +std::vector<std::string> Split(const std::string& str, + char delimiter, + bool trim_whitespaces, + bool purge_empty_strings) { + std::vector<std::string> tokens; + if (delimiter == 0) + return tokens; + + const char* sz = str.c_str(); + if (sz) { + const char* szNext = strchr(sz, delimiter); + while (szNext) { + if (szNext != sz || !purge_empty_strings) + tokens.emplace_back(sz, szNext - sz); + sz = szNext + 1; + szNext = strchr(sz, delimiter); + } + if (*sz != 0 || !purge_empty_strings) + tokens.emplace_back(sz); + } + + if (trim_whitespaces) { + std::for_each(tokens.begin(), tokens.end(), + [](std::string& str) { + base::TrimWhitespaceASCII(str, base::TRIM_ALL, &str); }); + } + + return tokens; +} + +std::pair<std::string, std::string> SplitAtFirst(const std::string& str, + char delimiter, + bool trim_whitespaces) { + std::pair<std::string, std::string> pair; + if (delimiter == 0) + return pair; + + const char* sz = str.c_str(); + const char* szNext = strchr(sz, delimiter); + if (szNext) { + pair.first = std::string(sz, szNext); + pair.second = std::string(szNext + 1); + } else { + pair.first = str; + } + + if (trim_whitespaces) { + base::TrimWhitespaceASCII(pair.first, base::TRIM_ALL, &pair.first); + base::TrimWhitespaceASCII(pair.second, base::TRIM_ALL, &pair.second); + } + + return pair; +} + +std::string Join(char delimiter, const std::vector<std::string>& strings) { + return JoinString(strings, delimiter); +} + +std::string Join(const std::string& delimiter, + const std::vector<std::string>& strings) { + return JoinString(strings, delimiter); +} + +std::string Join(char delimiter, + const std::string& str1, const std::string& str2) { + return str1 + delimiter + str2; +} + +std::string Join(const std::string& delimiter, + const std::string& str1, const std::string& str2) { + return str1 + delimiter + str2; +} + +std::string ToString(double value) { + return base::StringPrintf("%g", value); +} + +std::string ToString(bool value) { + return value ? "true" : "false"; +} + +} // namespace string_utils +} // namespace chromeos diff --git a/chromeos/strings/string_utils.h b/chromeos/strings/string_utils.h new file mode 100644 index 0000000..d5a9995 --- /dev/null +++ b/chromeos/strings/string_utils.h @@ -0,0 +1,56 @@ +// Copyright 2014 The Chromium OS Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef LIBCHROMEOS_CHROMEOS_STRINGS_STRING_UTILS_H_ +#define LIBCHROMEOS_CHROMEOS_STRINGS_STRING_UTILS_H_ + +#include <string> +#include <utility> +#include <vector> + +namespace chromeos { +namespace string_utils { + +// Treats the string as a delimited list of substrings and returns the array +// of original elements of the list. +// By default, empty elements from the original string are omitted and +// each element has all whitespaces trimmed off. +std::vector<std::string> Split(const std::string& str, + char delimiter, + bool trim_whitespaces = true, + bool purge_empty_strings = true); + +// Splits the string into two pieces at the first position of the specified +// delimiter. By default, each part has all whitespaces trimmed off. +std::pair<std::string, std::string> SplitAtFirst(const std::string& str, + char delimiter, + bool trim_whitespaces = true); + +// Joins an array of strings into a single string separated by |delimiter|. +std::string Join(char delimiter, const std::vector<std::string>& strings); +std::string Join(const std::string& delimiter, + const std::vector<std::string>& strings); +std::string Join(char delimiter, + const std::string& str1, const std::string& str2); +std::string Join(const std::string& delimiter, + const std::string& str1, const std::string& str2); + +// string_utils::ToString() is a helper function to convert any scalar type +// to a string. In most cases, it redirects the call to std::to_string with +// two exceptions: for std::string itself and for double and bool. +template<typename T> +inline std::string ToString(T value) { return std::to_string(value); } +// Having the following overload is handy for templates where the type +// of template parameter isn't known and could be a string itself. +inline std::string ToString(std::string value) { return value; } +// We overload this for double because std::to_string(double) uses %f to +// format the value and I would like to use a shorter %g format instead. +std::string ToString(double value); +// And the bool to be converted as true/false instead of 1/0. +std::string ToString(bool value); + +} // namespace string_utils +} // namespace chromeos + +#endif // LIBCHROMEOS_CHROMEOS_STRINGS_STRING_UTILS_H_ diff --git a/chromeos/strings/string_utils_unittest.cc b/chromeos/strings/string_utils_unittest.cc new file mode 100644 index 0000000..0842019 --- /dev/null +++ b/chromeos/strings/string_utils_unittest.cc @@ -0,0 +1,111 @@ +// Copyright (c) 2014 The Chromium OS Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include <chromeos/strings/string_utils.h> + +#include <gtest/gtest.h> + +namespace chromeos { + +TEST(StringUtils, Split) { + std::vector<std::string> parts; + + parts = string_utils::Split(",a,bc , d,,e,", ',', true, true); + EXPECT_EQ(4, parts.size()); + EXPECT_EQ("a", parts[0]); + EXPECT_EQ("bc", parts[1]); + EXPECT_EQ("d", parts[2]); + EXPECT_EQ("e", parts[3]); + + parts = string_utils::Split(",a,bc , d,,e,", ',', false, true); + EXPECT_EQ(4, parts.size()); + EXPECT_EQ("a", parts[0]); + EXPECT_EQ("bc ", parts[1]); + EXPECT_EQ(" d", parts[2]); + EXPECT_EQ("e", parts[3]); + + parts = string_utils::Split(",a,bc , d,,e,", ',', true, false); + EXPECT_EQ(7, parts.size()); + EXPECT_EQ("", parts[0]); + EXPECT_EQ("a", parts[1]); + EXPECT_EQ("bc", parts[2]); + EXPECT_EQ("d", parts[3]); + EXPECT_EQ("", parts[4]); + EXPECT_EQ("e", parts[5]); + EXPECT_EQ("", parts[6]); + + parts = string_utils::Split(",a,bc , d,,e,", ',', false, false); + EXPECT_EQ(7, parts.size()); + EXPECT_EQ("", parts[0]); + EXPECT_EQ("a", parts[1]); + EXPECT_EQ("bc ", parts[2]); + EXPECT_EQ(" d", parts[3]); + EXPECT_EQ("", parts[4]); + EXPECT_EQ("e", parts[5]); + EXPECT_EQ("", parts[6]); +} + +TEST(StringUtils, SplitAtFirst) { + std::pair<std::string, std::string> pair; + + pair = string_utils::SplitAtFirst(" 123 : 4 : 56 : 789 ", ':', true); + EXPECT_EQ("123", pair.first); + EXPECT_EQ("4 : 56 : 789", pair.second); + + pair = string_utils::SplitAtFirst(" 123 : 4 : 56 : 789 ", ':', false); + EXPECT_EQ(" 123 ", pair.first); + EXPECT_EQ(" 4 : 56 : 789 ", pair.second); + + pair = string_utils::SplitAtFirst("", '='); + EXPECT_EQ("", pair.first); + EXPECT_EQ("", pair.second); + + pair = string_utils::SplitAtFirst("=", '='); + EXPECT_EQ("", pair.first); + EXPECT_EQ("", pair.second); + + pair = string_utils::SplitAtFirst("a=", '='); + EXPECT_EQ("a", pair.first); + EXPECT_EQ("", pair.second); + + pair = string_utils::SplitAtFirst("abc=", '='); + EXPECT_EQ("abc", pair.first); + EXPECT_EQ("", pair.second); + + pair = string_utils::SplitAtFirst("=a", '='); + EXPECT_EQ("", pair.first); + EXPECT_EQ("a", pair.second); + + pair = string_utils::SplitAtFirst("=abc=", '='); + EXPECT_EQ("", pair.first); + EXPECT_EQ("abc=", pair.second); + + pair = string_utils::SplitAtFirst("abc", '='); + EXPECT_EQ("abc", pair.first); + EXPECT_EQ("", pair.second); +} + +TEST(StringUtils, Join_Char) { + EXPECT_EQ("", string_utils::Join(',', {})); + EXPECT_EQ("abc", string_utils::Join(',', {"abc"})); + EXPECT_EQ("abc,defg", string_utils::Join(',', {"abc", "defg"})); + EXPECT_EQ("1:2:3", string_utils::Join(':', {"1", "2", "3"})); + EXPECT_EQ("192.168.0.1", string_utils::Join('.', {"192", "168", "0", "1"})); + EXPECT_EQ("ff02::1", string_utils::Join(':', {"ff02", "", "1"})); +} + +TEST(StringUtils, Join_String) { + EXPECT_EQ("", string_utils::Join(",", {})); + EXPECT_EQ("abc", string_utils::Join(",", {"abc"})); + EXPECT_EQ("abc,defg", string_utils::Join(",", {"abc", "defg"})); + EXPECT_EQ("1 : 2 : 3", string_utils::Join(" : ", {"1", "2", "3"})); + EXPECT_EQ("123", string_utils::Join("", {"1", "2", "3"})); +} + +TEST(StringUtils, Join_Pair) { + EXPECT_EQ("ab,cd", string_utils::Join(',', "ab", "cd")); + EXPECT_EQ("key = value", string_utils::Join(" = ", "key", "value")); +} + +} // namespace chromeos |