proxygen
FixedStringTest.cpp
Go to the documentation of this file.
1 /*
2  * Copyright 2016-present Facebook, Inc.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 //
18 // Author: eniebler@fb.com
19 
20 #include <folly/FixedString.h>
22 
23 #define FS(x) ::folly::makeFixedString(x)
24 using namespace folly::string_literals;
25 
26 TEST(FixedStringExamples, Examples) {
27  // Example from the docs:
28  using namespace folly;
29  constexpr auto hello = makeFixedString("hello"); // a FixedString<5>
30  constexpr auto world = makeFixedString("world"); // another FixedString<5>
31  constexpr auto hello_world = hello + ' ' + world + '!';
32  static_assert(hello_world == "hello world!", "w00t");
33  EXPECT_STREQ("hello world!", hello_world.c_str());
34 
35  FixedString<10> test{"****"};
36  test.replace(1, 2, "!!!!");
37  EXPECT_STREQ("*!!!!*", test.c_str());
38  static_assert(makeFixedString("****").creplace(1, 2, "!!!!") == "*!!!!*", "");
39 }
40 
41 TEST(FixedStringCtorTest, Default) {
42  constexpr folly::FixedString<42> s{};
43  static_assert(s[0] == '\0', "");
44  static_assert(s.size() == 0u, "");
45 
46  constexpr auto s2 = s;
47  static_assert(s2[0] == '\0', "");
48  static_assert(s2.size() == 0u, "");
49 }
50 
51 TEST(FixedStringCtorTest, FromLiterals) {
52  constexpr folly::FixedString<42> s{"hello world"};
53  static_assert(s[0] == 'h', "");
54  constexpr folly::FixedString<11> s2{"hello world"};
55  static_assert(s2[0] == 'h', "");
56  static_assert(s2[10] == 'd', "");
57  static_assert(s2[11] == '\0', "");
58 
59  // Does not compile, hurray! :-)
60  // constexpr char a[1] = {'a'};
61  // constexpr folly::FixedString<10> s3(a);
62 }
63 
64 TEST(FixedStringCtorTest, FromPtrAndLength) {
65  constexpr folly::FixedString<11> s{"hello world", 11};
66  static_assert(s[0] == 'h', "");
67  static_assert(s[10] == 'd', "");
68  static_assert(s[11] == '\0', "");
69  static_assert(s.size() == 11u, "");
70 
71  constexpr folly::FixedString<5> s2{"hello world", 5};
72  static_assert(s2[0] == 'h', "");
73  static_assert(s2[4] == 'o', "");
74  static_assert(s2[5] == '\0', "");
75  static_assert(s2.size() == 5u, "");
76 
77  constexpr folly::FixedString<20> s3{"hello world", 5};
78  static_assert(s2[0] == 'h', "");
79  static_assert(s2[4] == 'o', "");
80  static_assert(s2[5] == '\0', "");
81  static_assert(s2.size() == 5u, "");
82 
83  static_assert("hello" == s3, "");
84  static_assert(s3 == "hello", "");
85  static_assert(s3 == s2, "");
86  static_assert("hell" != s3, "");
87  static_assert(s3 != "helloooo", "");
88  static_assert(!(s3 != s2), "");
89 }
90 
91 TEST(FixedStringCtorTest, FromStringAndOffset) {
92  constexpr folly::FixedString<11> s{"hello world"};
93  constexpr folly::FixedString<5> s2{s, 6u, npos};
94  static_assert(s2 == "world", "");
95  constexpr folly::FixedString<0> s3{s, 11u, npos};
96  static_assert(s3 == "", "");
97  // Out of bounds offset, does not compile
98  // constexpr folly::FixedString<0> s4{s, 12};
99 }
100 
101 TEST(FixedStringCtorTest, FromStringOffsetAndCount) {
102  constexpr folly::FixedString<11> s{"hello world"};
103  constexpr folly::FixedString<4> s2{s, 6u, 4u};
104  static_assert(s2 == "worl", "");
105  constexpr folly::FixedString<5> s3{s, 6u, 5u};
106  static_assert(s3 == "world", "");
107  // Out of bounds count, does not compile:
108  // constexpr folly::FixedString<5> s4{s, 6, 6};
109 }
110 
111 TEST(FixedStringCtorTest, FromInitializerList) {
112  constexpr folly::FixedString<11> s{
113  'h', 'e', 'l', 'l', 'o', ' ', 'w', 'o', 'r', 'l', 'd'};
114  static_assert(s == "hello world", "");
115  // Out of bounds count, does not compile:
116  // constexpr folly::FixedString<10> s{
117  // {'h','e','l','l','o',' ','w','o','r','l','d'}};
118 }
119 
120 TEST(FixedStringCtorTest, FromUDL) {
121  using namespace folly::literals;
122 #if defined(__GNUC__)
123  constexpr auto x = "hello"_fs;
124  static_assert(
125  std::is_same<decltype(x), const folly::FixedString<5>>::value, "");
126  static_assert(x[0] == 'h', "");
127  static_assert(x[1] == 'e', "");
128  static_assert(x[2] == 'l', "");
129  static_assert(x[3] == 'l', "");
130  static_assert(x[4] == 'o', "");
131  static_assert(x[5] == '\0', "");
132  static_assert(x.size() == 5u, "");
133 #endif
134 
135  constexpr auto y = "goodbye"_fs8;
136  static_assert(
137  std::is_same<decltype(y), const folly::FixedString<8>>::value, "");
138  static_assert(y.size() == 7u, "");
139  static_assert(y == "goodbye", "");
140 
141  constexpr auto z = "now is the time for all good llamas"_fs64;
142  static_assert(
143  std::is_same<decltype(z), const folly::FixedString<64>>::value, "");
144  static_assert(z.size() == 35u, "");
145  static_assert(z == "now is the time for all good llamas", "");
146 }
147 
148 TEST(FixedStringConcatTest, FromStringAndLiteral) {
149  constexpr folly::FixedString<42> s{"hello world"};
150  constexpr auto res = s + "!!!";
151  static_assert(res.size() == 14u, "");
152  static_assert(res == "hello world!!!", "");
153 }
154 
155 TEST(FixedStringConcatTest, FromTwoStrings) {
156  constexpr folly::FixedString<42> s{"hello world"};
157  constexpr auto res = s + "!!!";
158  static_assert(res.size() == 14u, "");
159  static_assert(res == "hello world!!!", "");
160 }
161 
162 #if FOLLY_USE_CPP14_CONSTEXPR
163 constexpr folly::FixedString<20> constexpr_swap_test() {
164  folly::FixedString<10> tmp1{"hello"}, tmp2{"world!"};
165  tmp2.swap(tmp1);
166  return tmp1 + tmp2;
167 }
168 
169 TEST(FixedStringSwapTest, ConstexprSwap) {
170  static_assert(constexpr_swap_test() == "world!hello", "");
171 }
172 #endif
173 
174 TEST(FixedStringSwapTest, RuntimeSwap) {
175  folly::FixedString<10> tmp1{"hello"}, tmp2{"world!"};
176  tmp2.swap(tmp1);
177  EXPECT_STREQ((tmp1 + tmp2).c_str(), "world!hello");
178 }
179 
180 #if FOLLY_USE_CPP14_CONSTEXPR
181 constexpr folly::FixedString<10> constexpr_assign_string_test_1() {
182  folly::FixedString<10> tmp1, tmp2{"world!"};
183  tmp1 = tmp2;
184  return tmp1;
185 }
186 constexpr folly::FixedString<10> constexpr_assign_string_test_2() {
187  folly::FixedString<10> tmp{"aaaaaaaaaa"};
188  tmp.assign("hello"_fs8);
189  return tmp;
190 }
191 constexpr folly::FixedString<10> constexpr_assign_string_test_3() {
192  folly::FixedString<10> tmp{"aaaaaaaaaa"};
193  tmp.assign("goodbye"_fs8, 3u, 2u);
194  return tmp;
195 }
196 constexpr folly::FixedString<10> constexpr_assign_string_test_4() {
197  folly::FixedString<10> tmp{"aaaaaaaaaa"};
198  tmp.assign("goodbye"_fs8, 3u, npos);
199  return tmp;
200 }
201 
202 TEST(FixedStringAssignTest, ConstexprAssignString) {
203  static_assert(constexpr_assign_string_test_1() == "world!", "");
204  static_assert(constexpr_assign_string_test_2() == "hello", "");
205  static_assert(constexpr_assign_string_test_3() == "db", "");
206  static_assert(constexpr_assign_string_test_4() == "dbye", "");
207 }
208 #endif
209 
210 TEST(FixedStringAssignTest, RuntimeAssignString) {
211  folly::FixedString<10> tmp1, tmp2{"world!"};
212  tmp1 = tmp2;
213  EXPECT_STREQ(tmp1.c_str(), "world!");
214  tmp1.assign("goodbye"_fs8);
215  EXPECT_STREQ("goodbye", tmp1.c_str());
216  tmp1.assign("goodbye"_fs8, 3u, npos);
217  EXPECT_STREQ("dbye", tmp1.c_str());
218  tmp1.assign("goodbye"_fs8, 3u, 3u);
219  EXPECT_STREQ("dby", tmp1.c_str());
220 }
221 
222 #if FOLLY_USE_CPP14_CONSTEXPR
223 constexpr folly::FixedString<10> constexpr_assign_literal_test_1() {
224  folly::FixedString<10> tmp{"aaaaaaaaaa"};
225  tmp = "hello";
226  // Not null-terminated, does not compile:
227  // using C = const char[1];
228  // tmp = C{'a'};
229  return tmp;
230 }
231 constexpr folly::FixedString<10> constexpr_assign_literal_test_2() {
232  folly::FixedString<10> tmp{"aaaaaaaaaa"};
233  tmp.assign("hello");
234  return tmp;
235 }
236 constexpr folly::FixedString<10> constexpr_assign_literal_test_3() {
237  folly::FixedString<10> tmp{"aaaaaaaaaa"};
238  tmp.assign("goodbye", 4u);
239  return tmp;
240 }
241 
242 TEST(FixedStringAssignTest, ConstexprAssignLiteral) {
243  static_assert(constexpr_assign_literal_test_1() == "hello", "");
244  static_assert(constexpr_assign_literal_test_2() == "hello", "");
245  static_assert(constexpr_assign_literal_test_3() == "good", "");
246 }
247 #endif
248 
249 TEST(FixedStringAssignTest, RuntimeAssignLiteral) {
250  folly::FixedString<10> tmp{"aaaaaaaaaa"};
251  tmp = "hello";
252  EXPECT_STREQ("hello", tmp.c_str());
253  tmp.assign("goodbye");
254  EXPECT_STREQ("goodbye", tmp.c_str());
255  tmp.assign("goodbye", 4u);
256  EXPECT_STREQ("good", tmp.c_str());
257 }
258 
259 TEST(FixedStringIndexTest, Index) {
260  constexpr folly::FixedString<11> digits{"0123456789"};
261  static_assert(digits[0] == '0', "");
262  static_assert(digits[1] == '1', "");
263  static_assert(digits[2] == '2', "");
264  static_assert(digits[9] == '9', "");
265  static_assert(digits[10] == '\0', "");
266 #ifdef NDEBUG
267  // This should be allowed and work in constexpr mode since the internal array
268  // is actually big enough and op[] does no parameter validation:
269  static_assert(digits[11] == '\0', "");
270 #endif
271 
272  static_assert(digits.at(0) == '0', "");
273  static_assert(digits.at(1) == '1', "");
274  static_assert(digits.at(2) == '2', "");
275  static_assert(digits.at(9) == '9', "");
276  static_assert(digits.at(10) == '\0', "");
277  EXPECT_THROW(digits.at(11), std::out_of_range);
278 }
279 
280 TEST(FixedStringCompareTest, Compare) {
281  constexpr folly::FixedString<10> tmp1{"aaaaaaaaaa"};
282  constexpr folly::FixedString<12> tmp2{"aaaaaaaaaba"};
283  static_assert(-1 == tmp1.compare(tmp2), "");
284  static_assert(1 == tmp2.compare(tmp1), "");
285  static_assert(0 == tmp2.compare(tmp2), "");
286  static_assert(tmp1 < tmp2, "");
287  static_assert(tmp1 <= tmp2, "");
288  static_assert(tmp2 > tmp1, "");
289  static_assert(tmp2 >= tmp1, "");
290  static_assert(tmp2 == tmp2, ""); // @nolint
291  static_assert(tmp2 <= tmp2, ""); // @nolint
292  static_assert(tmp2 >= tmp2, ""); // @nolint
293  static_assert(!(tmp2 < tmp2), "");
294  static_assert(!(tmp2 > tmp2), "");
295 
296  constexpr folly::FixedString<10> tmp3{"aaa"};
297  constexpr folly::FixedString<12> tmp4{"aaaa"};
298  static_assert(-1 == tmp3.compare(tmp4), "");
299  static_assert(1 == tmp4.compare(tmp3), "");
300  static_assert(tmp3 < tmp4, "");
301  static_assert(tmp3 <= tmp4, "");
302  static_assert(tmp4 > tmp3, "");
303  static_assert(tmp4 >= tmp3, "");
304  static_assert(tmp3 < "aaaa", "");
305  static_assert(tmp3 <= "aaaa", "");
306  static_assert(!(tmp3 == tmp4), "");
307  static_assert(tmp3 != tmp4, "");
308  static_assert("aaaa" > tmp3, "");
309  static_assert("aaaa" >= tmp3, "");
310  static_assert("aaaa" != tmp3, "");
311  static_assert("aaa" == tmp3, "");
312  static_assert(tmp3 != "aaaa", "");
313  static_assert(tmp3 == "aaa", "");
314 }
315 
316 TEST(FixedStringCompareTest, CompareStdString) {
317  constexpr folly::FixedString<10> tmp1{"aaaaaaaaaa"};
318  std::string const tmp2{"aaaaaaaaaba"};
319  EXPECT_EQ(-1, tmp1.compare(tmp2));
320  // These are specifically testing the operators, and so we can't rely
321  // on whever the implementation details of EXPECT_<OP> might be.
322  EXPECT_FALSE(tmp1 == tmp2);
323  EXPECT_FALSE(tmp2 == tmp1);
324  EXPECT_TRUE(tmp1 != tmp2);
325  EXPECT_TRUE(tmp2 != tmp1);
326  EXPECT_TRUE(tmp1 < tmp2);
327  EXPECT_FALSE(tmp2 < tmp1);
328  EXPECT_TRUE(tmp1 <= tmp2);
329  EXPECT_FALSE(tmp2 <= tmp1);
330  EXPECT_FALSE(tmp1 > tmp2);
331  EXPECT_TRUE(tmp2 > tmp1);
332  EXPECT_FALSE(tmp1 >= tmp2);
333  EXPECT_TRUE(tmp2 >= tmp1);
334 }
335 
336 #if FOLLY_USE_CPP14_CONSTEXPR
337 constexpr folly::FixedString<20> constexpr_append_string_test() {
338  folly::FixedString<20> a{"hello"}, b{"X world!"};
339  a.append(1u, ' ');
340  a.append(b, 2u, 5u);
341  a.append(b, 7u, 1u);
342  return a;
343 }
344 
345 TEST(FixedStringAssignTest, ConstexprAppendString) {
346  static_assert(constexpr_append_string_test() == "hello world!", "");
347 }
348 #endif
349 
350 TEST(FixedStringAssignTest, RuntimeAppendString) {
351  folly::FixedString<20> a{"hello"}, b{"X world!"};
352  a.append(1u, ' ');
353  a.append(b, 2u, 5u);
354  a.append(b, 7u, 1u);
355  EXPECT_STREQ("hello world!", a.c_str());
356 }
357 
358 #if FOLLY_USE_CPP14_CONSTEXPR
359 constexpr folly::FixedString<20> constexpr_append_literal_test() {
360  folly::FixedString<20> a{"hello"};
361  a.append(1u, ' ');
362  a.append("X world!" + 2u, 5u);
363  a.append("X world!" + 7u);
364  return a;
365 }
366 
367 TEST(FixedStringAssignTest, ConstexprAppendLiteral) {
368  static_assert(constexpr_append_literal_test() == "hello world!", "");
369 }
370 #endif
371 
372 TEST(FixedStringAssignTest, RuntimeAppendLiteral) {
373  folly::FixedString<20> a{"hello"};
374  a.append(1u, ' ');
375  a.append("X world!" + 2u, 5u);
376  a.append("X world!" + 7u);
377  EXPECT_STREQ("hello world!", a.c_str());
378 }
379 
380 TEST(FixedStringCAppendTest, CAppendString) {
381  constexpr folly::FixedString<10> a{"hello"}, b{"X world!"};
382  constexpr auto tmp1 = a.cappend(' ');
383  constexpr auto tmp2 = tmp1.cappend(b, 2u, 5u);
384  constexpr auto tmp3 = tmp2.cappend(b, 7u, 1u);
385  static_assert(tmp3 == "hello world!", "");
386 }
387 
388 TEST(FixedStringCAppendTest, CAppendLiteral) {
389  constexpr folly::FixedString<10> a{"hello"};
390  constexpr auto tmp1 = a.cappend(' ');
391  constexpr auto tmp2 = tmp1.cappend("X world!", 2u, 5u);
392  constexpr auto tmp3 = tmp2.cappend("X world!", 7u, 1u);
393  static_assert(tmp3 == "hello world!", "");
394 }
395 
396 #if FOLLY_USE_CPP14_CONSTEXPR
397 constexpr folly::FixedString<10> constexpr_replace_string_test() {
398  folly::FixedString<10> tmp{"abcdefghij"};
399  tmp.replace(1, 5, FS("XX"));
400  return tmp;
401 }
402 
403 TEST(FixedStringReplaceTest, ConstexprReplaceString) {
404  static_assert(constexpr_replace_string_test().size() == 7u, "");
405  static_assert(constexpr_replace_string_test() == "aXXghij", "");
406 }
407 #endif
408 
409 TEST(FixedStringReplaceTest, RuntimeReplaceString) {
410  folly::FixedString<10> tmp{"abcdefghij"};
411  tmp.replace(1, 5, FS("XX"));
412  EXPECT_EQ(7u, tmp.size());
413  EXPECT_STREQ("aXXghij", tmp.c_str());
414 }
415 
416 TEST(FixedStringEraseTest, RuntimeEraseTest) {
417  auto x = FS("abcdefghijklmnopqrstuvwxyz"), y = x;
418  x.erase(x.size());
419  EXPECT_EQ(26u, x.size());
420  EXPECT_STREQ(y.c_str(), x.c_str());
421  x.erase(25u).erase(24u);
422  EXPECT_EQ(24u, x.size());
423  EXPECT_STREQ("abcdefghijklmnopqrstuvwx", x.c_str());
424  x.erase(1u, x.size() - 2u);
425  EXPECT_EQ(2u, x.size());
426  EXPECT_STREQ("ax", x.c_str());
427 }
428 
429 TEST(FixedStringEraseTest, CEraseTest) {
430  constexpr auto x = FS("abcdefghijklmnopqrstuvwxyz"), y = x;
431  constexpr auto tmp0 = x.cerase(x.size());
432  static_assert(26u == tmp0.size(), "");
433  static_assert(y == tmp0, "");
434  constexpr auto tmp1 = tmp0.cerase(25u).cerase(24u);
435  static_assert(24u == tmp1.size(), "");
436  static_assert("abcdefghijklmnopqrstuvwx" == tmp1, "");
437  constexpr auto tmp2 = tmp1.cerase(1u, tmp1.size() - 2u);
438  static_assert(2u == tmp2.size(), "");
439  static_assert("ax" == tmp2, "");
440  constexpr auto tmp3 = tmp2.cerase();
441  static_assert("" == tmp3, "");
442 }
443 
444 TEST(FixedStringFindTest, FindString) {
445  constexpr folly::FixedString<10> tmp{"hijdefghij"};
446  static_assert(tmp.find(FS("hij")) == 0u, "");
447  static_assert(tmp.find(FS("hij"), 1u) == 7u, "");
448  static_assert(tmp.find(FS("hijdefghij")) == 0u, "");
449  static_assert(tmp.find(FS("")) == 0u, "");
450 }
451 
452 TEST(FixedStringFindTest, FindLiteral) {
453  constexpr folly::FixedString<10> tmp{"hijdefghij"};
454  static_assert(tmp.find("hij") == 0u, "");
455  static_assert(tmp.find("hij", 1u) == 7u, "");
456  static_assert(tmp.find("hijdefghij") == 0u, "");
457 }
458 
459 TEST(FixedStringReverseFindTest, FindChar) {
460  constexpr folly::FixedString<16> tmp{"This is a string"};
461  static_assert(tmp.find('s') == 3u, "");
462  static_assert(tmp.find('s', 9u) == 10u, "");
463  static_assert(tmp.find('s', 10u) == 10u, "");
464  static_assert(tmp.find('s', 11u) == tmp.npos, "");
465 }
466 
467 TEST(FixedStringReverseFindTest, ReverseFindString) {
468  constexpr folly::FixedString<16> tmp{"This is a string"};
469  static_assert(tmp.rfind(FS("is")) == 5u, "");
470  static_assert(tmp.rfind(FS("is"), 4u) == 2u, "");
471  static_assert(tmp.rfind(FS("This is a string")) == 0u, "");
472  static_assert(tmp.rfind(FS("This is a string!")) == tmp.npos, "");
473  static_assert(tmp.rfind(FS("")) == 16u, "");
474 }
475 
476 TEST(FixedStringReverseFindTest, ReverseFindLiteral) {
477  constexpr folly::FixedString<16> tmp{"This is a string"};
478  static_assert(tmp.rfind("is") == 5u, "");
479  static_assert(tmp.rfind("is", 4u) == 2u, "");
480  static_assert(tmp.rfind("This is a string") == 0u, "");
481  static_assert(tmp.rfind("This is a string!") == tmp.npos, "");
482  static_assert(tmp.rfind("") == 16u, "");
483 }
484 
485 TEST(FixedStringReverseFindTest, ReverseFindChar) {
486  constexpr folly::FixedString<16> tmp{"This is a string"};
487  static_assert(tmp.rfind('s') == 10u, "");
488  static_assert(tmp.rfind('s', 5u) == 3u, "");
489  static_assert(tmp.rfind('s', 3u) == 3u, "");
490  static_assert(tmp.rfind('s', 2u) == tmp.npos, "");
491 }
492 
493 TEST(FixedStringFindFirstOfTest, FindFirstOfString) {
494  constexpr folly::FixedString<16> tmp{"This is a string"};
495  static_assert(tmp.find_first_of(FS("hi")) == 1u, "");
496  static_assert(tmp.find_first_of(FS("xi")) == 2u, "");
497  static_assert(tmp.find_first_of(FS("xi"), 6u) == 13u, "");
498  static_assert(tmp.find_first_of(FS("xz")) == tmp.npos, "");
499  static_assert(FS("a").find_first_of(FS("cba")) == 0u, "");
500  static_assert(FS("").find_first_of(FS("cba")) == tmp.npos, "");
501  static_assert(FS("a").find_first_of(FS("")) == tmp.npos, "");
502  static_assert(FS("").find_first_of(FS("")) == tmp.npos, "");
503 }
504 
505 TEST(FixedStringFindFirstOfTest, FindFirstOfLiteral) {
506  constexpr folly::FixedString<16> tmp{"This is a string"};
507  static_assert(tmp.find_first_of("hi") == 1u, "");
508  static_assert(tmp.find_first_of("xi") == 2u, "");
509  static_assert(tmp.find_first_of("xi", 6u) == 13u, "");
510  static_assert(tmp.find_first_of("xis", 6u, 2u) == 13u, "");
511  static_assert(tmp.find_first_of("xz") == tmp.npos, "");
512  static_assert(FS("a").find_first_of("cba") == 0u, "");
513  static_assert(FS("").find_first_of("cba") == tmp.npos, "");
514  static_assert(FS("a").find_first_of("") == tmp.npos, "");
515  static_assert(FS("").find_first_of("") == tmp.npos, "");
516 }
517 
518 TEST(FixedStringFindFirstOfTest, FindFirstOfChar) {
519  constexpr folly::FixedString<16> tmp{"This is a string"};
520  static_assert(tmp.find_first_of('h') == 1u, "");
521  static_assert(tmp.find_first_of('i') == 2u, "");
522  static_assert(tmp.find_first_of('i', 6u) == 13u, "");
523  static_assert(tmp.find_first_of('x') == tmp.npos, "");
524  static_assert(FS("a").find_first_of('a') == 0u, "");
525  static_assert(FS("").find_first_of('a') == tmp.npos, "");
526 }
527 
528 TEST(FixedStringFindFirstNotOfTest, FindFirstNotOfString) {
529  constexpr folly::FixedString<16> tmp{"This is a string"};
530  static_assert(tmp.find_first_not_of(FS("Ti")) == 1u, "");
531  static_assert(tmp.find_first_not_of(FS("hT")) == 2u, "");
532  static_assert(tmp.find_first_not_of(FS("s atr"), 6u) == 13u, "");
533  static_assert(tmp.find_first_not_of(FS("This atrng")) == tmp.npos, "");
534  static_assert(FS("a").find_first_not_of(FS("X")) == 0u, "");
535  static_assert(FS("").find_first_not_of(FS("cba")) == tmp.npos, "");
536  static_assert(FS("a").find_first_not_of(FS("")) == 0u, "");
537  static_assert(FS("").find_first_not_of(FS("")) == tmp.npos, "");
538 }
539 
540 TEST(FixedStringFindFirstNotOfTest, FindFirstNotOfLiteral) {
541  constexpr folly::FixedString<16> tmp{"This is a string"};
542  static_assert(tmp.find_first_not_of("Ti") == 1u, "");
543  static_assert(tmp.find_first_not_of("hT") == 2u, "");
544  static_assert(tmp.find_first_not_of("s atr", 6u) == 13u, "");
545  static_assert(tmp.find_first_not_of("This atrng") == tmp.npos, "");
546  static_assert(FS("a").find_first_not_of("X") == 0u, "");
547  static_assert(FS("").find_first_not_of("cba") == tmp.npos, "");
548  static_assert(FS("a").find_first_not_of("") == 0u, "");
549  static_assert(FS("").find_first_not_of("") == tmp.npos, "");
550 }
551 
552 TEST(FixedStringFindFirstNotOfTest, FindFirstNotOfChar) {
553  constexpr folly::FixedString<16> tmp{"This is a string"};
554  static_assert(tmp.find_first_not_of('T') == 1u, "");
555  static_assert(tmp.find_first_not_of('i') == 0u, "");
556  static_assert(tmp.find_first_not_of('x', 6u) == 6u, "");
557  static_assert(tmp.find_first_not_of('s', 6u) == 7u, "");
558  static_assert(FS("a").find_first_not_of('a') == tmp.npos, "");
559  static_assert(FS("").find_first_not_of('a') == tmp.npos, "");
560 }
561 
562 TEST(FixedStringFindLastOfTest, FindLastOfString) {
563  constexpr folly::FixedString<16> tmp{"This is a string"};
564  static_assert(tmp.find_last_of(FS("hi")) == 13u, "");
565  static_assert(tmp.find_last_of(FS("xh")) == 1u, "");
566  static_assert(tmp.find_last_of(FS("xi"), 6u) == 5u, "");
567  static_assert(tmp.find_last_of(FS("xz")) == tmp.npos, "");
568  static_assert(FS("a").find_last_of(FS("cba")) == 0u, "");
569  static_assert(FS("").find_last_of(FS("cba")) == tmp.npos, "");
570  static_assert(FS("a").find_last_of(FS("")) == tmp.npos, "");
571  static_assert(FS("").find_last_of(FS("")) == tmp.npos, "");
572 }
573 
574 TEST(FixedStringFindLastOfTest, FindLastOfLiteral) {
575  constexpr folly::FixedString<16> tmp{"This is a string"};
576  static_assert(tmp.find_last_of("hi") == 13u, "");
577  static_assert(tmp.find_last_of("xh") == 1u, "");
578  static_assert(tmp.find_last_of("xi", 6u) == 5u, "");
579  static_assert(tmp.find_last_of("xis", 6u, 2u) == 5u, "");
580  static_assert(tmp.find_last_of("xz") == tmp.npos, "");
581  static_assert(FS("a").find_last_of("cba") == 0u, "");
582  static_assert(FS("").find_last_of("cba") == tmp.npos, "");
583  static_assert(FS("a").find_last_of("") == tmp.npos, "");
584  static_assert(FS("").find_last_of("") == tmp.npos, "");
585 }
586 
587 TEST(FixedStringFindLastOfTest, FindLastOfChar) {
588  constexpr folly::FixedString<16> tmp{"This is a string"};
589  static_assert(tmp.find_last_of('h') == 1u, "");
590  static_assert(tmp.find_last_of('i') == 13u, "");
591  static_assert(tmp.find_last_of('i', 6u) == 5u, "");
592  static_assert(tmp.find_last_of('x') == tmp.npos, "");
593  static_assert(FS("a").find_last_of('a') == 0u, "");
594  static_assert(FS("").find_last_of('a') == tmp.npos, "");
595 }
596 
597 TEST(FixedStringFindLastNotOfTest, FindLastNotOfString) {
598  constexpr folly::FixedString<16> tmp{"This is a string"};
599  static_assert(tmp.find_last_not_of(FS("gstrin")) == 9u, "");
600  static_assert(tmp.find_last_not_of(FS("hT")) == 15u, "");
601  static_assert(tmp.find_last_not_of(FS("s atr"), 6u) == 5u, "");
602  static_assert(tmp.find_last_not_of(FS("This atrng")) == tmp.npos, "");
603  static_assert(FS("a").find_last_not_of(FS("X")) == 0u, "");
604  static_assert(FS("").find_last_not_of(FS("cba")) == tmp.npos, "");
605  static_assert(FS("a").find_last_not_of(FS("")) == 0u, "");
606  static_assert(FS("").find_last_not_of(FS("")) == tmp.npos, "");
607 }
608 
609 TEST(FixedStringFindLastNotOfTest, FindLastNotOfLiteral) {
610  constexpr folly::FixedString<16> tmp{"This is a string"};
611  static_assert(tmp.find_last_not_of("gstrin") == 9u, "");
612  static_assert(tmp.find_last_not_of("hT") == 15u, "");
613  static_assert(tmp.find_last_not_of("s atr", 6u) == 5u, "");
614  static_assert(tmp.find_last_not_of(" atrs", 6u, 4u) == 6u, "");
615  static_assert(tmp.find_last_not_of("This atrng") == tmp.npos, "");
616  static_assert(FS("a").find_last_not_of("X") == 0u, "");
617  static_assert(FS("").find_last_not_of("cba") == tmp.npos, "");
618  static_assert(FS("a").find_last_not_of("") == 0u, "");
619  static_assert(FS("").find_last_not_of("") == tmp.npos, "");
620 }
621 
622 TEST(FixedStringFindLastNotOfTest, FindLastNotOfChar) {
623  constexpr folly::FixedString<16> tmp{"This is a string"};
624  static_assert(tmp.find_last_not_of('g') == 14u, "");
625  static_assert(tmp.find_last_not_of('i') == 15u, "");
626  static_assert(tmp.find_last_not_of('x', 6u) == 6u, "");
627  static_assert(tmp.find_last_not_of('s', 6u) == 5u, "");
628  static_assert(FS("a").find_last_not_of('a') == tmp.npos, "");
629  static_assert(FS("").find_last_not_of('a') == tmp.npos, "");
630 }
631 
632 TEST(FixedStringConversionTest, ConversionToStdString) {
633  constexpr folly::FixedString<16> tmp{"This is a string"};
634  std::string str = tmp;
635  EXPECT_STREQ("This is a string", str.c_str());
636  str = "another string"_fs16;
637  EXPECT_STREQ("another string", str.c_str());
638 }
639 
640 #if FOLLY_USE_CPP14_CONSTEXPR
641 constexpr std::size_t countSpacesReverse(folly::FixedString<50> s) {
642  std::size_t count = 0u;
643  auto i = s.rbegin();
644  for (; i != s.rend(); ++i, --i, i++, i--, i += 1, i -= 1, i += 1) {
645  if (' ' == *i) {
646  ++count;
647  }
648  }
649  return count;
650 }
651 
652 TEST(FixedStringReverseIteratorTest, Cpp14ConstexprReverseIteration) {
653  static_assert(3 == countSpacesReverse("This is a string"), "");
654 }
655 #endif
656 
657 TEST(FixedStringReverseIteratorTest, ConstexprReverseIteration) {
658  static constexpr auto alpha = FS("abcdefghijklmnopqrstuvwxyz");
659  static_assert('a' == alpha.rbegin()[25], "");
660  static_assert('a' == *(alpha.rbegin() + 25), "");
661  static_assert('c' == *(alpha.rbegin() + 25 - 2), "");
662  static_assert((alpha.rend() - 2) == (alpha.rbegin() + 24), "");
663 }
664 
665 namespace GCC61971 {
666 // FixedString runs afoul of GCC #61971 (spurious -Warray-bounds)
667 // in optimized builds. The following test case triggers it for gcc-4.x.
668 // Test that FixedString suppresses the warning correctly.
669 // https://gcc.gnu.org/bugzilla/show_bug.cgi?id=61971
670 constexpr auto xyz = folly::makeFixedString("xyz");
671 constexpr auto dot = folly::makeFixedString(".");
672 
673 template <typename T1>
674 constexpr auto concatStuff(const T1& component) noexcept {
675  return xyz + dot + component;
676 }
677 constexpr auto co = folly::makeFixedString("co");
678 
679 struct S {
681 };
682 } // namespace GCC61971
683 
684 TEST(FixedStringGCC61971, GCC61971) {
685  GCC61971::S s;
686  (void)s;
687 }
688 
689 #include <folly/Range.h>
690 
691 TEST(FixedStringConversionTest, ConversionToFollyRange) {
692  // The following declaraction is static for compilers that haven't implemented
693  // the resolution of:
694  // http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#1454
695  static constexpr folly::FixedString<16> tmp{"This is a string"};
696  constexpr folly::StringPiece piece = tmp;
697  static_assert(tmp.begin() == piece.begin(), "");
698  static_assert(tmp.end() == piece.end(), "");
699 }
Definition: InvokeTest.cpp:58
#define EXPECT_THROW(statement, expected_exception)
Definition: gtest.h:1843
char b
#define EXPECT_EQ(val1, val2)
Definition: gtest.h:1922
const int x
—— Concurrent Priority Queue Implementation ——
Definition: AtomicBitSet.h:29
requires E e noexcept(noexcept(s.error(std::move(e))))
FOLLY_CPP14_CONSTEXPR BasicFixedString & assign(std::size_t count, Char ch) noexcept(false)
Definition: FixedString.h:844
constexpr auto concatStuff(const T1 &component) noexcept
FOLLY_CPP14_CONSTEXPR void swap(BasicFixedString &that) noexcept
Definition: FixedString.h:942
#define EXPECT_STREQ(s1, s2)
Definition: gtest.h:1995
constexpr auto size(C const &c) -> decltype(c.size())
Definition: Access.h:45
constexpr const Char * c_str() const noexcept
Definition: FixedString.h:969
A class for holding up to N characters of type Char that is amenable to constexpr string manipulation...
Definition: FixedString.h:42
Definition: InvokeTest.cpp:72
char a
int * count
#define EXPECT_TRUE(condition)
Definition: gtest.h:1859
#define FS(x)
constexpr auto co
FOLLY_CPP14_CONSTEXPR reverse_iterator rend() noexcept
Definition: FixedString.h:1041
const char * string
Definition: Conv.cpp:212
static set< string > s
uint64_t value(const typename LockFreeRingBuffer< T, Atom >::Cursor &rbcursor)
Definition: InvokeTest.cpp:65
#define EXPECT_FALSE(condition)
Definition: gtest.h:1862
FOLLY_CPP14_CONSTEXPR BasicFixedString & replace(const Char *first, const Char *last, const BasicFixedString< Char, M > &that) noexcept(false)
Definition: FixedString.h:1663
constexpr auto xyz
TEST(SequencedExecutor, CPUThreadPoolExecutor)
FOLLY_CPP14_CONSTEXPR reverse_iterator rbegin() noexcept
Definition: FixedString.h:1019
constexpr BasicFixedString< Char, N-1u > makeFixedString(const Char(&a)[N]) noexcept
Definition: FixedString.h:2991
constexpr auto dot