str_cat_test.cc
Go to the documentation of this file.
00001 // Copyright 2017 The Abseil Authors.
00002 //
00003 // Licensed under the Apache License, Version 2.0 (the "License");
00004 // you may not use this file except in compliance with the License.
00005 // You may obtain a copy of the License at
00006 //
00007 //      https://www.apache.org/licenses/LICENSE-2.0
00008 //
00009 // Unless required by applicable law or agreed to in writing, software
00010 // distributed under the License is distributed on an "AS IS" BASIS,
00011 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
00012 // See the License for the specific language governing permissions and
00013 // limitations under the License.
00014 
00015 // Unit tests for all str_cat.h functions
00016 
00017 #include "absl/strings/str_cat.h"
00018 
00019 #include <cstdint>
00020 #include <string>
00021 #include <vector>
00022 
00023 #include "gtest/gtest.h"
00024 #include "absl/strings/substitute.h"
00025 
00026 #ifdef __ANDROID__
00027 // Android assert messages only go to system log, so death tests cannot inspect
00028 // the message for matching.
00029 #define ABSL_EXPECT_DEBUG_DEATH(statement, regex) \
00030   EXPECT_DEBUG_DEATH(statement, ".*")
00031 #else
00032 #define ABSL_EXPECT_DEBUG_DEATH(statement, regex) \
00033   EXPECT_DEBUG_DEATH(statement, regex)
00034 #endif
00035 
00036 namespace {
00037 
00038 // Test absl::StrCat of ints and longs of various sizes and signdedness.
00039 TEST(StrCat, Ints) {
00040   const short s = -1;  // NOLINT(runtime/int)
00041   const uint16_t us = 2;
00042   const int i = -3;
00043   const unsigned int ui = 4;
00044   const long l = -5;                 // NOLINT(runtime/int)
00045   const unsigned long ul = 6;        // NOLINT(runtime/int)
00046   const long long ll = -7;           // NOLINT(runtime/int)
00047   const unsigned long long ull = 8;  // NOLINT(runtime/int)
00048   const ptrdiff_t ptrdiff = -9;
00049   const size_t size = 10;
00050   const intptr_t intptr = -12;
00051   const uintptr_t uintptr = 13;
00052   std::string answer;
00053   answer = absl::StrCat(s, us);
00054   EXPECT_EQ(answer, "-12");
00055   answer = absl::StrCat(i, ui);
00056   EXPECT_EQ(answer, "-34");
00057   answer = absl::StrCat(l, ul);
00058   EXPECT_EQ(answer, "-56");
00059   answer = absl::StrCat(ll, ull);
00060   EXPECT_EQ(answer, "-78");
00061   answer = absl::StrCat(ptrdiff, size);
00062   EXPECT_EQ(answer, "-910");
00063   answer = absl::StrCat(ptrdiff, intptr);
00064   EXPECT_EQ(answer, "-9-12");
00065   answer = absl::StrCat(uintptr, 0);
00066   EXPECT_EQ(answer, "130");
00067 }
00068 
00069 TEST(StrCat, Enums) {
00070   enum SmallNumbers { One = 1, Ten = 10 } e = Ten;
00071   EXPECT_EQ("10", absl::StrCat(e));
00072   EXPECT_EQ("-5", absl::StrCat(SmallNumbers(-5)));
00073 
00074   enum class Option { Boxers = 1, Briefs = -1 };
00075 
00076   EXPECT_EQ("-1", absl::StrCat(Option::Briefs));
00077 
00078   enum class Airplane : uint64_t {
00079     Airbus = 1,
00080     Boeing = 1000,
00081     Canary = 10000000000  // too big for "int"
00082   };
00083 
00084   EXPECT_EQ("10000000000", absl::StrCat(Airplane::Canary));
00085 
00086   enum class TwoGig : int32_t {
00087     TwoToTheZero = 1,
00088     TwoToTheSixteenth = 1 << 16,
00089     TwoToTheThirtyFirst = INT32_MIN
00090   };
00091   EXPECT_EQ("65536", absl::StrCat(TwoGig::TwoToTheSixteenth));
00092   EXPECT_EQ("-2147483648", absl::StrCat(TwoGig::TwoToTheThirtyFirst));
00093   EXPECT_EQ("-1", absl::StrCat(static_cast<TwoGig>(-1)));
00094 
00095   enum class FourGig : uint32_t {
00096     TwoToTheZero = 1,
00097     TwoToTheSixteenth = 1 << 16,
00098     TwoToTheThirtyFirst = 1U << 31  // too big for "int"
00099   };
00100   EXPECT_EQ("65536", absl::StrCat(FourGig::TwoToTheSixteenth));
00101   EXPECT_EQ("2147483648", absl::StrCat(FourGig::TwoToTheThirtyFirst));
00102   EXPECT_EQ("4294967295", absl::StrCat(static_cast<FourGig>(-1)));
00103 
00104   EXPECT_EQ("10000000000", absl::StrCat(Airplane::Canary));
00105 }
00106 
00107 TEST(StrCat, Basics) {
00108   std::string result;
00109 
00110   std::string strs[] = {"Hello", "Cruel", "World"};
00111 
00112   std::string stdstrs[] = {
00113     "std::Hello",
00114     "std::Cruel",
00115     "std::World"
00116   };
00117 
00118   absl::string_view pieces[] = {"Hello", "Cruel", "World"};
00119 
00120   const char* c_strs[] = {
00121     "Hello",
00122     "Cruel",
00123     "World"
00124   };
00125 
00126   int32_t i32s[] = {'H', 'C', 'W'};
00127   uint64_t ui64s[] = {12345678910LL, 10987654321LL};
00128 
00129   EXPECT_EQ(absl::StrCat(), "");
00130 
00131   result = absl::StrCat(false, true, 2, 3);
00132   EXPECT_EQ(result, "0123");
00133 
00134   result = absl::StrCat(-1);
00135   EXPECT_EQ(result, "-1");
00136 
00137   result = absl::StrCat(absl::SixDigits(0.5));
00138   EXPECT_EQ(result, "0.5");
00139 
00140   result = absl::StrCat(strs[1], pieces[2]);
00141   EXPECT_EQ(result, "CruelWorld");
00142 
00143   result = absl::StrCat(stdstrs[1], " ", stdstrs[2]);
00144   EXPECT_EQ(result, "std::Cruel std::World");
00145 
00146   result = absl::StrCat(strs[0], ", ", pieces[2]);
00147   EXPECT_EQ(result, "Hello, World");
00148 
00149   result = absl::StrCat(strs[0], ", ", strs[1], " ", strs[2], "!");
00150   EXPECT_EQ(result, "Hello, Cruel World!");
00151 
00152   result = absl::StrCat(pieces[0], ", ", pieces[1], " ", pieces[2]);
00153   EXPECT_EQ(result, "Hello, Cruel World");
00154 
00155   result = absl::StrCat(c_strs[0], ", ", c_strs[1], " ", c_strs[2]);
00156   EXPECT_EQ(result, "Hello, Cruel World");
00157 
00158   result = absl::StrCat("ASCII ", i32s[0], ", ", i32s[1], " ", i32s[2], "!");
00159   EXPECT_EQ(result, "ASCII 72, 67 87!");
00160 
00161   result = absl::StrCat(ui64s[0], ", ", ui64s[1], "!");
00162   EXPECT_EQ(result, "12345678910, 10987654321!");
00163 
00164   std::string one =
00165       "1";  // Actually, it's the size of this std::string that we want; a
00166             // 64-bit build distinguishes between size_t and uint64_t,
00167             // even though they're both unsigned 64-bit values.
00168   result = absl::StrCat("And a ", one.size(), " and a ",
00169                         &result[2] - &result[0], " and a ", one, " 2 3 4", "!");
00170   EXPECT_EQ(result, "And a 1 and a 2 and a 1 2 3 4!");
00171 
00172   // result = absl::StrCat("Single chars won't compile", '!');
00173   // result = absl::StrCat("Neither will nullptrs", nullptr);
00174   result =
00175       absl::StrCat("To output a char by ASCII/numeric value, use +: ", '!' + 0);
00176   EXPECT_EQ(result, "To output a char by ASCII/numeric value, use +: 33");
00177 
00178   float f = 100000.5;
00179   result = absl::StrCat("A hundred K and a half is ", absl::SixDigits(f));
00180   EXPECT_EQ(result, "A hundred K and a half is 100000");
00181 
00182   f = 100001.5;
00183   result =
00184       absl::StrCat("A hundred K and one and a half is ", absl::SixDigits(f));
00185   EXPECT_EQ(result, "A hundred K and one and a half is 100002");
00186 
00187   double d = 100000.5;
00188   d *= d;
00189   result =
00190       absl::StrCat("A hundred K and a half squared is ", absl::SixDigits(d));
00191   EXPECT_EQ(result, "A hundred K and a half squared is 1.00001e+10");
00192 
00193   result = absl::StrCat(1, 2, 333, 4444, 55555, 666666, 7777777, 88888888,
00194                         999999999);
00195   EXPECT_EQ(result, "12333444455555666666777777788888888999999999");
00196 }
00197 
00198 // A minimal allocator that uses malloc().
00199 template <typename T>
00200 struct Mallocator {
00201   typedef T value_type;
00202   typedef size_t size_type;
00203   typedef ptrdiff_t difference_type;
00204   typedef T* pointer;
00205   typedef const T* const_pointer;
00206   typedef T& reference;
00207   typedef const T& const_reference;
00208 
00209   size_type max_size() const {
00210     return size_t(std::numeric_limits<size_type>::max()) / sizeof(value_type);
00211   }
00212   template <typename U>
00213   struct rebind {
00214     typedef Mallocator<U> other;
00215   };
00216   Mallocator() = default;
00217   template <class U>
00218   Mallocator(const Mallocator<U>&) {}  // NOLINT(runtime/explicit)
00219 
00220   T* allocate(size_t n) { return static_cast<T*>(std::malloc(n * sizeof(T))); }
00221   void deallocate(T* p, size_t) { std::free(p); }
00222 };
00223 template <typename T, typename U>
00224 bool operator==(const Mallocator<T>&, const Mallocator<U>&) {
00225   return true;
00226 }
00227 template <typename T, typename U>
00228 bool operator!=(const Mallocator<T>&, const Mallocator<U>&) {
00229   return false;
00230 }
00231 
00232 TEST(StrCat, CustomAllocator) {
00233   using mstring =
00234       std::basic_string<char, std::char_traits<char>, Mallocator<char>>;
00235   const mstring str1("PARACHUTE OFF A BLIMP INTO MOSCONE!!");
00236 
00237   const mstring str2("Read this book about coffee tables");
00238 
00239   std::string result = absl::StrCat(str1, str2);
00240   EXPECT_EQ(result,
00241             "PARACHUTE OFF A BLIMP INTO MOSCONE!!"
00242             "Read this book about coffee tables");
00243 }
00244 
00245 TEST(StrCat, MaxArgs) {
00246   std::string result;
00247   // Test 10 up to 26 arguments, the old maximum
00248   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a");
00249   EXPECT_EQ(result, "123456789a");
00250   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b");
00251   EXPECT_EQ(result, "123456789ab");
00252   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c");
00253   EXPECT_EQ(result, "123456789abc");
00254   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c", "d");
00255   EXPECT_EQ(result, "123456789abcd");
00256   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c", "d", "e");
00257   EXPECT_EQ(result, "123456789abcde");
00258   result =
00259       absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c", "d", "e", "f");
00260   EXPECT_EQ(result, "123456789abcdef");
00261   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c", "d", "e", "f",
00262                         "g");
00263   EXPECT_EQ(result, "123456789abcdefg");
00264   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c", "d", "e", "f",
00265                         "g", "h");
00266   EXPECT_EQ(result, "123456789abcdefgh");
00267   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c", "d", "e", "f",
00268                         "g", "h", "i");
00269   EXPECT_EQ(result, "123456789abcdefghi");
00270   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c", "d", "e", "f",
00271                         "g", "h", "i", "j");
00272   EXPECT_EQ(result, "123456789abcdefghij");
00273   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c", "d", "e", "f",
00274                         "g", "h", "i", "j", "k");
00275   EXPECT_EQ(result, "123456789abcdefghijk");
00276   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c", "d", "e", "f",
00277                         "g", "h", "i", "j", "k", "l");
00278   EXPECT_EQ(result, "123456789abcdefghijkl");
00279   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c", "d", "e", "f",
00280                         "g", "h", "i", "j", "k", "l", "m");
00281   EXPECT_EQ(result, "123456789abcdefghijklm");
00282   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c", "d", "e", "f",
00283                         "g", "h", "i", "j", "k", "l", "m", "n");
00284   EXPECT_EQ(result, "123456789abcdefghijklmn");
00285   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c", "d", "e", "f",
00286                         "g", "h", "i", "j", "k", "l", "m", "n", "o");
00287   EXPECT_EQ(result, "123456789abcdefghijklmno");
00288   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c", "d", "e", "f",
00289                         "g", "h", "i", "j", "k", "l", "m", "n", "o", "p");
00290   EXPECT_EQ(result, "123456789abcdefghijklmnop");
00291   result = absl::StrCat(1, 2, 3, 4, 5, 6, 7, 8, 9, "a", "b", "c", "d", "e", "f",
00292                         "g", "h", "i", "j", "k", "l", "m", "n", "o", "p", "q");
00293   EXPECT_EQ(result, "123456789abcdefghijklmnopq");
00294   // No limit thanks to C++11's variadic templates
00295   result = absl::StrCat(
00296       1, 2, 3, 4, 5, 6, 7, 8, 9, 10, "a", "b", "c", "d", "e", "f", "g", "h",
00297       "i", "j", "k", "l", "m", "n", "o", "p", "q", "r", "s", "t", "u", "v", "w",
00298       "x", "y", "z", "A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L",
00299       "M", "N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z");
00300   EXPECT_EQ(result,
00301             "12345678910abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ");
00302 }
00303 
00304 TEST(StrAppend, Basics) {
00305   std::string result = "existing text";
00306 
00307   std::string strs[] = {"Hello", "Cruel", "World"};
00308 
00309   std::string stdstrs[] = {
00310     "std::Hello",
00311     "std::Cruel",
00312     "std::World"
00313   };
00314 
00315   absl::string_view pieces[] = {"Hello", "Cruel", "World"};
00316 
00317   const char* c_strs[] = {
00318     "Hello",
00319     "Cruel",
00320     "World"
00321   };
00322 
00323   int32_t i32s[] = {'H', 'C', 'W'};
00324   uint64_t ui64s[] = {12345678910LL, 10987654321LL};
00325 
00326   std::string::size_type old_size = result.size();
00327   absl::StrAppend(&result);
00328   EXPECT_EQ(result.size(), old_size);
00329 
00330   old_size = result.size();
00331   absl::StrAppend(&result, strs[0]);
00332   EXPECT_EQ(result.substr(old_size), "Hello");
00333 
00334   old_size = result.size();
00335   absl::StrAppend(&result, strs[1], pieces[2]);
00336   EXPECT_EQ(result.substr(old_size), "CruelWorld");
00337 
00338   old_size = result.size();
00339   absl::StrAppend(&result, stdstrs[0], ", ", pieces[2]);
00340   EXPECT_EQ(result.substr(old_size), "std::Hello, World");
00341 
00342   old_size = result.size();
00343   absl::StrAppend(&result, strs[0], ", ", stdstrs[1], " ", strs[2], "!");
00344   EXPECT_EQ(result.substr(old_size), "Hello, std::Cruel World!");
00345 
00346   old_size = result.size();
00347   absl::StrAppend(&result, pieces[0], ", ", pieces[1], " ", pieces[2]);
00348   EXPECT_EQ(result.substr(old_size), "Hello, Cruel World");
00349 
00350   old_size = result.size();
00351   absl::StrAppend(&result, c_strs[0], ", ", c_strs[1], " ", c_strs[2]);
00352   EXPECT_EQ(result.substr(old_size), "Hello, Cruel World");
00353 
00354   old_size = result.size();
00355   absl::StrAppend(&result, "ASCII ", i32s[0], ", ", i32s[1], " ", i32s[2], "!");
00356   EXPECT_EQ(result.substr(old_size), "ASCII 72, 67 87!");
00357 
00358   old_size = result.size();
00359   absl::StrAppend(&result, ui64s[0], ", ", ui64s[1], "!");
00360   EXPECT_EQ(result.substr(old_size), "12345678910, 10987654321!");
00361 
00362   std::string one =
00363       "1";  // Actually, it's the size of this std::string that we want; a
00364             // 64-bit build distinguishes between size_t and uint64_t,
00365             // even though they're both unsigned 64-bit values.
00366   old_size = result.size();
00367   absl::StrAppend(&result, "And a ", one.size(), " and a ",
00368                   &result[2] - &result[0], " and a ", one, " 2 3 4", "!");
00369   EXPECT_EQ(result.substr(old_size), "And a 1 and a 2 and a 1 2 3 4!");
00370 
00371   // result = absl::StrCat("Single chars won't compile", '!');
00372   // result = absl::StrCat("Neither will nullptrs", nullptr);
00373   old_size = result.size();
00374   absl::StrAppend(&result,
00375                   "To output a char by ASCII/numeric value, use +: ", '!' + 0);
00376   EXPECT_EQ(result.substr(old_size),
00377             "To output a char by ASCII/numeric value, use +: 33");
00378 
00379   // Test 9 arguments, the old maximum
00380   old_size = result.size();
00381   absl::StrAppend(&result, 1, 22, 333, 4444, 55555, 666666, 7777777, 88888888,
00382                   9);
00383   EXPECT_EQ(result.substr(old_size), "1223334444555556666667777777888888889");
00384 
00385   // No limit thanks to C++11's variadic templates
00386   old_size = result.size();
00387   absl::StrAppend(
00388       &result, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10,                           //
00389       "a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m",  //
00390       "n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z",  //
00391       "A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M",  //
00392       "N", "O", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z",  //
00393       "No limit thanks to C++11's variadic templates");
00394   EXPECT_EQ(result.substr(old_size),
00395             "12345678910abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ"
00396             "No limit thanks to C++11's variadic templates");
00397 }
00398 
00399 TEST(StrCat, VectorBoolReferenceTypes) {
00400   std::vector<bool> v;
00401   v.push_back(true);
00402   v.push_back(false);
00403   std::vector<bool> const& cv = v;
00404   // Test that vector<bool>::reference and vector<bool>::const_reference
00405   // are handled as if the were really bool types and not the proxy types
00406   // they really are.
00407   std::string result = absl::StrCat(v[0], v[1], cv[0], cv[1]); // NOLINT
00408   EXPECT_EQ(result, "1010");
00409 }
00410 
00411 // Passing nullptr to memcpy is undefined behavior and this test
00412 // provides coverage of codepaths that handle empty strings with nullptrs.
00413 TEST(StrCat, AvoidsMemcpyWithNullptr) {
00414   EXPECT_EQ(absl::StrCat(42, absl::string_view{}), "42");
00415 
00416   // Cover CatPieces code.
00417   EXPECT_EQ(absl::StrCat(1, 2, 3, 4, 5, absl::string_view{}), "12345");
00418 
00419   // Cover AppendPieces.
00420   std::string result;
00421   absl::StrAppend(&result, 1, 2, 3, 4, 5, absl::string_view{});
00422   EXPECT_EQ(result, "12345");
00423 }
00424 
00425 #ifdef GTEST_HAS_DEATH_TEST
00426 TEST(StrAppend, Death) {
00427   std::string s = "self";
00428   // on linux it's "assertion", on mac it's "Assertion",
00429   // on chromiumos it's "Assertion ... failed".
00430   ABSL_EXPECT_DEBUG_DEATH(absl::StrAppend(&s, s.c_str() + 1),
00431                           "ssertion.*failed");
00432   ABSL_EXPECT_DEBUG_DEATH(absl::StrAppend(&s, s), "ssertion.*failed");
00433 }
00434 #endif  // GTEST_HAS_DEATH_TEST
00435 
00436 TEST(StrAppend, EmptyString) {
00437   std::string s = "";
00438   absl::StrAppend(&s, s);
00439   EXPECT_EQ(s, "");
00440 }
00441 
00442 template <typename IntType>
00443 void CheckHex(IntType v, const char* nopad_format, const char* zeropad_format,
00444               const char* spacepad_format) {
00445   char expected[256];
00446 
00447   std::string actual = absl::StrCat(absl::Hex(v, absl::kNoPad));
00448   snprintf(expected, sizeof(expected), nopad_format, v);
00449   EXPECT_EQ(expected, actual) << " decimal value " << v;
00450 
00451   for (int spec = absl::kZeroPad2; spec <= absl::kZeroPad20; ++spec) {
00452     std::string actual =
00453         absl::StrCat(absl::Hex(v, static_cast<absl::PadSpec>(spec)));
00454     snprintf(expected, sizeof(expected), zeropad_format,
00455              spec - absl::kZeroPad2 + 2, v);
00456     EXPECT_EQ(expected, actual) << " decimal value " << v;
00457   }
00458 
00459   for (int spec = absl::kSpacePad2; spec <= absl::kSpacePad20; ++spec) {
00460     std::string actual =
00461         absl::StrCat(absl::Hex(v, static_cast<absl::PadSpec>(spec)));
00462     snprintf(expected, sizeof(expected), spacepad_format,
00463              spec - absl::kSpacePad2 + 2, v);
00464     EXPECT_EQ(expected, actual) << " decimal value " << v;
00465   }
00466 }
00467 
00468 template <typename IntType>
00469 void CheckDec(IntType v, const char* nopad_format, const char* zeropad_format,
00470               const char* spacepad_format) {
00471   char expected[256];
00472 
00473   std::string actual = absl::StrCat(absl::Dec(v, absl::kNoPad));
00474   snprintf(expected, sizeof(expected), nopad_format, v);
00475   EXPECT_EQ(expected, actual) << " decimal value " << v;
00476 
00477   for (int spec = absl::kZeroPad2; spec <= absl::kZeroPad20; ++spec) {
00478     std::string actual =
00479         absl::StrCat(absl::Dec(v, static_cast<absl::PadSpec>(spec)));
00480     snprintf(expected, sizeof(expected), zeropad_format,
00481              spec - absl::kZeroPad2 + 2, v);
00482     EXPECT_EQ(expected, actual)
00483         << " decimal value " << v << " format '" << zeropad_format
00484         << "' digits " << (spec - absl::kZeroPad2 + 2);
00485   }
00486 
00487   for (int spec = absl::kSpacePad2; spec <= absl::kSpacePad20; ++spec) {
00488     std::string actual =
00489         absl::StrCat(absl::Dec(v, static_cast<absl::PadSpec>(spec)));
00490     snprintf(expected, sizeof(expected), spacepad_format,
00491              spec - absl::kSpacePad2 + 2, v);
00492     EXPECT_EQ(expected, actual)
00493         << " decimal value " << v << " format '" << spacepad_format
00494         << "' digits " << (spec - absl::kSpacePad2 + 2);
00495   }
00496 }
00497 
00498 void CheckHexDec64(uint64_t v) {
00499   unsigned long long ullv = v;  // NOLINT(runtime/int)
00500 
00501   CheckHex(ullv, "%llx", "%0*llx", "%*llx");
00502   CheckDec(ullv, "%llu", "%0*llu", "%*llu");
00503 
00504   long long llv = static_cast<long long>(ullv);  // NOLINT(runtime/int)
00505   CheckDec(llv, "%lld", "%0*lld", "%*lld");
00506 
00507   if (sizeof(v) == sizeof(&v)) {
00508     auto uintptr = static_cast<uintptr_t>(v);
00509     void* ptr = reinterpret_cast<void*>(uintptr);
00510     CheckHex(ptr, "%llx", "%0*llx", "%*llx");
00511   }
00512 }
00513 
00514 void CheckHexDec32(uint32_t uv) {
00515   CheckHex(uv, "%x", "%0*x", "%*x");
00516   CheckDec(uv, "%u", "%0*u", "%*u");
00517   int32_t v = static_cast<int32_t>(uv);
00518   CheckDec(v, "%d", "%0*d", "%*d");
00519 
00520   if (sizeof(v) == sizeof(&v)) {
00521     auto uintptr = static_cast<uintptr_t>(v);
00522     void* ptr = reinterpret_cast<void*>(uintptr);
00523     CheckHex(ptr, "%x", "%0*x", "%*x");
00524   }
00525 }
00526 
00527 void CheckAll(uint64_t v) {
00528   CheckHexDec64(v);
00529   CheckHexDec32(static_cast<uint32_t>(v));
00530 }
00531 
00532 void TestFastPrints() {
00533   // Test all small ints; there aren't many and they're common.
00534   for (int i = 0; i < 10000; i++) {
00535     CheckAll(i);
00536   }
00537 
00538   CheckAll(std::numeric_limits<uint64_t>::max());
00539   CheckAll(std::numeric_limits<uint64_t>::max() - 1);
00540   CheckAll(std::numeric_limits<int64_t>::min());
00541   CheckAll(std::numeric_limits<int64_t>::min() + 1);
00542   CheckAll(std::numeric_limits<uint32_t>::max());
00543   CheckAll(std::numeric_limits<uint32_t>::max() - 1);
00544   CheckAll(std::numeric_limits<int32_t>::min());
00545   CheckAll(std::numeric_limits<int32_t>::min() + 1);
00546   CheckAll(999999999);              // fits in 32 bits
00547   CheckAll(1000000000);             // fits in 32 bits
00548   CheckAll(9999999999);             // doesn't fit in 32 bits
00549   CheckAll(10000000000);            // doesn't fit in 32 bits
00550   CheckAll(999999999999999999);     // fits in signed 64-bit
00551   CheckAll(9999999999999999999u);   // fits in unsigned 64-bit, but not signed.
00552   CheckAll(1000000000000000000);    // fits in signed 64-bit
00553   CheckAll(10000000000000000000u);  // fits in unsigned 64-bit, but not signed.
00554 
00555   CheckAll(999999999876543210);    // check all decimal digits, signed
00556   CheckAll(9999999999876543210u);  // check all decimal digits, unsigned.
00557   CheckAll(0x123456789abcdef0);    // check all hex digits
00558   CheckAll(0x12345678);
00559 
00560   int8_t minus_one_8bit = -1;
00561   EXPECT_EQ("ff", absl::StrCat(absl::Hex(minus_one_8bit)));
00562 
00563   int16_t minus_one_16bit = -1;
00564   EXPECT_EQ("ffff", absl::StrCat(absl::Hex(minus_one_16bit)));
00565 }
00566 
00567 TEST(Numbers, TestFunctionsMovedOverFromNumbersMain) {
00568   TestFastPrints();
00569 }
00570 
00571 }  // namespace


abseil_cpp
Author(s):
autogenerated on Wed Jun 19 2019 19:42:15