1 // RUN: %check_clang_tidy %s readability-container-size-empty %t -- -- -fno-delayed-template-parsing 2 3 namespace std { 4 template <typename T> struct vector { 5 vector(); 6 bool operator==(const vector<T>& other) const; 7 bool operator!=(const vector<T>& other) const; 8 unsigned long size() const; 9 bool empty() const; 10 }; 11 12 template <typename T> struct basic_string { 13 basic_string(); 14 bool operator==(const basic_string<T>& other) const; 15 bool operator!=(const basic_string<T>& other) const; 16 bool operator==(const char *) const; 17 bool operator!=(const char *) const; 18 basic_string<T> operator+(const basic_string<T>& other) const; 19 unsigned long size() const; 20 bool empty() const; 21 }; 22 23 typedef basic_string<char> string; 24 typedef basic_string<wchar_t> wstring; 25 26 inline namespace __v2 { 27 template <typename T> struct set { 28 set(); 29 bool operator==(const set<T>& other) const; 30 bool operator!=(const set<T>& other) const; 31 unsigned long size() const; 32 bool empty() const; 33 }; 34 } 35 36 } 37 38 template <typename T> 39 class TemplatedContainer { 40 public: 41 bool operator==(const TemplatedContainer<T>& other) const; 42 bool operator!=(const TemplatedContainer<T>& other) const; 43 int size() const; 44 bool empty() const; 45 }; 46 47 template <typename T> 48 class PrivateEmpty { 49 public: 50 bool operator==(const PrivateEmpty<T>& other) const; 51 bool operator!=(const PrivateEmpty<T>& other) const; 52 int size() const; 53 private: 54 bool empty() const; 55 }; 56 57 struct BoolSize { 58 bool size() const; 59 bool empty() const; 60 }; 61 62 struct EnumSize { 63 enum E { one }; 64 enum E size() const; 65 bool empty() const; 66 }; 67 68 class Container { 69 public: 70 bool operator==(const Container& other) const; 71 int size() const; 72 bool empty() const; 73 }; 74 75 class Derived : public Container { 76 }; 77 78 class Container2 { 79 public: 80 int size() const; empty() const81 bool empty() const { return size() == 0; } 82 }; 83 84 class Container3 { 85 public: 86 int size() const; 87 bool empty() const; 88 }; 89 empty() const90bool Container3::empty() const { return this->size() == 0; } 91 92 class Container4 { 93 public: 94 bool operator==(const Container4& rhs) const; 95 int size() const; empty() const96 bool empty() const { return *this == Container4(); } 97 }; 98 99 struct Lazy { sizeLazy100 constexpr unsigned size() const { return 0; } emptyLazy101 constexpr bool empty() const { return true; } 102 }; 103 s_func()104std::string s_func() { 105 return std::string(); 106 } 107 takesBool(bool)108void takesBool(bool) 109 { 110 111 } 112 returnsBool()113bool returnsBool() { 114 std::set<int> intSet; 115 std::string str; 116 std::string str2; 117 std::wstring wstr; 118 (void)(str.size() + 0); 119 (void)(str.size() - 0); 120 (void)(0 + str.size()); 121 (void)(0 - str.size()); 122 if (intSet.size() == 0) 123 ; 124 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used to check for emptiness instead of 'size' [readability-container-size-empty] 125 // CHECK-FIXES: {{^ }}if (intSet.empty()){{$}} 126 // CHECK-MESSAGES: :32:8: note: method 'set'::empty() defined here 127 if (intSet == std::set<int>()) 128 ; 129 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used to check for emptiness 130 // CHECK-FIXES: {{^ }}if (intSet.empty()){{$}} 131 // CHECK-MESSAGES: :32:8: note: method 'set'::empty() defined here 132 if (s_func() == "") 133 ; 134 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 135 // CHECK-FIXES: {{^ }}if (s_func().empty()){{$}} 136 if (str.size() == 0) 137 ; 138 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 139 // CHECK-FIXES: {{^ }}if (str.empty()){{$}} 140 if ((str + str2).size() == 0) 141 ; 142 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 143 // CHECK-FIXES: {{^ }}if ((str + str2).empty()){{$}} 144 if (str == "") 145 ; 146 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 147 // CHECK-FIXES: {{^ }}if (str.empty()){{$}} 148 if (str + str2 == "") 149 ; 150 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 151 // CHECK-FIXES: {{^ }}if ((str + str2).empty()){{$}} 152 if (wstr.size() == 0) 153 ; 154 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 155 // CHECK-FIXES: {{^ }}if (wstr.empty()){{$}} 156 if (wstr == "") 157 ; 158 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 159 // CHECK-FIXES: {{^ }}if (wstr.empty()){{$}} 160 std::vector<int> vect; 161 if (vect.size() == 0) 162 ; 163 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 164 // CHECK-FIXES: {{^ }}if (vect.empty()){{$}} 165 if (vect == std::vector<int>()) 166 ; 167 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 168 // CHECK-FIXES: {{^ }}if (vect.empty()){{$}} 169 if (vect.size() != 0) 170 ; 171 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 172 // CHECK-FIXES: {{^ }}if (!vect.empty()){{$}} 173 if (vect != std::vector<int>()) 174 ; 175 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 176 // CHECK-FIXES: {{^ }}if (!vect.empty()){{$}} 177 if (0 == vect.size()) 178 ; 179 // CHECK-MESSAGES: :[[@LINE-2]]:12: warning: the 'empty' method should be used 180 // CHECK-FIXES: {{^ }}if (vect.empty()){{$}} 181 if (0 != vect.size()) 182 ; 183 // CHECK-MESSAGES: :[[@LINE-2]]:12: warning: the 'empty' method should be used 184 // CHECK-FIXES: {{^ }}if (!vect.empty()){{$}} 185 if (std::vector<int>() == vect) 186 ; 187 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 188 // CHECK-FIXES: {{^ }}if (vect.empty()){{$}} 189 if (std::vector<int>() != vect) 190 ; 191 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 192 // CHECK-FIXES: {{^ }}if (!vect.empty()){{$}} 193 if (vect.size() > 0) 194 ; 195 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 196 // CHECK-FIXES: {{^ }}if (!vect.empty()){{$}} 197 if (0 < vect.size()) 198 ; 199 // CHECK-MESSAGES: :[[@LINE-2]]:11: warning: the 'empty' method should be used 200 // CHECK-FIXES: {{^ }}if (!vect.empty()){{$}} 201 if (vect.size() < 1) 202 ; 203 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 204 // CHECK-FIXES: {{^ }}if (vect.empty()){{$}} 205 if (1 > vect.size()) 206 ; 207 // CHECK-MESSAGES: :[[@LINE-2]]:11: warning: the 'empty' method should be used 208 // CHECK-FIXES: {{^ }}if (vect.empty()){{$}} 209 if (vect.size() >= 1) 210 ; 211 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 212 // CHECK-FIXES: {{^ }}if (!vect.empty()){{$}} 213 if (1 <= vect.size()) 214 ; 215 // CHECK-MESSAGES: :[[@LINE-2]]:12: warning: the 'empty' method should be used 216 // CHECK-FIXES: {{^ }}if (!vect.empty()){{$}} 217 if (vect.size() > 1) // no warning 218 ; 219 if (1 < vect.size()) // no warning 220 ; 221 if (vect.size() <= 1) // no warning 222 ; 223 if (1 >= vect.size()) // no warning 224 ; 225 if (!vect.size()) 226 ; 227 // CHECK-MESSAGES: :[[@LINE-2]]:8: warning: the 'empty' method should be used 228 // CHECK-FIXES: {{^ }}if (vect.empty()){{$}} 229 if (vect.size()) 230 ; 231 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 232 // CHECK-FIXES: {{^ }}if (!vect.empty()){{$}} 233 234 if (vect.empty()) 235 ; 236 237 const std::vector<int> vect2; 238 if (vect2.size() != 0) 239 ; 240 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 241 // CHECK-FIXES: {{^ }}if (!vect2.empty()){{$}} 242 243 std::vector<int> *vect3 = new std::vector<int>(); 244 if (vect3->size() == 0) 245 ; 246 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 247 // CHECK-FIXES: {{^ }}if (vect3->empty()){{$}} 248 if ((*vect3).size() == 0) 249 ; 250 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 251 // CHECK-FIXES: {{^ }}if ((*vect3).empty()){{$}} 252 if ((*vect3) == std::vector<int>()) 253 ; 254 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 255 // CHECK-FIXES: {{^ }}if (vect3->empty()){{$}} 256 if (*vect3 == std::vector<int>()) 257 ; 258 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 259 // CHECK-FIXES: {{^ }}if (vect3->empty()){{$}} 260 261 delete vect3; 262 263 const std::vector<int> &vect4 = vect2; 264 if (vect4.size() == 0) 265 ; 266 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 267 // CHECK-FIXES: {{^ }}if (vect4.empty()){{$}} 268 if (vect4 == std::vector<int>()) 269 ; 270 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 271 // CHECK-FIXES: {{^ }}if (vect4.empty()){{$}} 272 273 TemplatedContainer<void> templated_container; 274 if (templated_container.size() == 0) 275 ; 276 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 277 // CHECK-FIXES: {{^ }}if (templated_container.empty()){{$}} 278 if (templated_container == TemplatedContainer<void>()) 279 ; 280 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 281 // CHECK-FIXES: {{^ }}if (templated_container.empty()){{$}} 282 if (templated_container.size() != 0) 283 ; 284 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 285 // CHECK-FIXES: {{^ }}if (!templated_container.empty()){{$}} 286 if (templated_container != TemplatedContainer<void>()) 287 ; 288 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 289 // CHECK-FIXES: {{^ }}if (!templated_container.empty()){{$}} 290 if (0 == templated_container.size()) 291 ; 292 // CHECK-MESSAGES: :[[@LINE-2]]:12: warning: the 'empty' method should be used 293 // CHECK-FIXES: {{^ }}if (templated_container.empty()){{$}} 294 if (TemplatedContainer<void>() == templated_container) 295 ; 296 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 297 // CHECK-FIXES: {{^ }}if (templated_container.empty()){{$}} 298 if (0 != templated_container.size()) 299 ; 300 // CHECK-MESSAGES: :[[@LINE-2]]:12: warning: the 'empty' method should be used 301 // CHECK-FIXES: {{^ }}if (!templated_container.empty()){{$}} 302 if (TemplatedContainer<void>() != templated_container) 303 ; 304 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 305 // CHECK-FIXES: {{^ }}if (!templated_container.empty()){{$}} 306 if (templated_container.size() > 0) 307 ; 308 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 309 // CHECK-FIXES: {{^ }}if (!templated_container.empty()){{$}} 310 if (0 < templated_container.size()) 311 ; 312 // CHECK-MESSAGES: :[[@LINE-2]]:11: warning: the 'empty' method should be used 313 // CHECK-FIXES: {{^ }}if (!templated_container.empty()){{$}} 314 if (templated_container.size() < 1) 315 ; 316 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 317 // CHECK-FIXES: {{^ }}if (templated_container.empty()){{$}} 318 if (1 > templated_container.size()) 319 ; 320 // CHECK-MESSAGES: :[[@LINE-2]]:11: warning: the 'empty' method should be used 321 // CHECK-FIXES: {{^ }}if (templated_container.empty()){{$}} 322 if (templated_container.size() >= 1) 323 ; 324 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 325 // CHECK-FIXES: {{^ }}if (!templated_container.empty()){{$}} 326 if (1 <= templated_container.size()) 327 ; 328 // CHECK-MESSAGES: :[[@LINE-2]]:12: warning: the 'empty' method should be used 329 // CHECK-FIXES: {{^ }}if (!templated_container.empty()){{$}} 330 if (templated_container.size() > 1) // no warning 331 ; 332 if (1 < templated_container.size()) // no warning 333 ; 334 if (templated_container.size() <= 1) // no warning 335 ; 336 if (1 >= templated_container.size()) // no warning 337 ; 338 if (!templated_container.size()) 339 ; 340 // CHECK-MESSAGES: :[[@LINE-2]]:8: warning: the 'empty' method should be used 341 // CHECK-FIXES: {{^ }}if (templated_container.empty()){{$}} 342 if (templated_container.size()) 343 ; 344 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 345 // CHECK-FIXES: {{^ }}if (!templated_container.empty()){{$}} 346 347 if (templated_container.empty()) 348 ; 349 350 // No warnings expected. 351 PrivateEmpty<void> private_empty; 352 if (private_empty.size() == 0) 353 ; 354 if (private_empty == PrivateEmpty<void>()) 355 ; 356 if (private_empty.size() != 0) 357 ; 358 if (private_empty != PrivateEmpty<void>()) 359 ; 360 if (0 == private_empty.size()) 361 ; 362 if (PrivateEmpty<void>() == private_empty) 363 ; 364 if (0 != private_empty.size()) 365 ; 366 if (PrivateEmpty<void>() != private_empty) 367 ; 368 if (private_empty.size() > 0) 369 ; 370 if (0 < private_empty.size()) 371 ; 372 if (private_empty.size() < 1) 373 ; 374 if (1 > private_empty.size()) 375 ; 376 if (private_empty.size() >= 1) 377 ; 378 if (1 <= private_empty.size()) 379 ; 380 if (private_empty.size() > 1) 381 ; 382 if (1 < private_empty.size()) 383 ; 384 if (private_empty.size() <= 1) 385 ; 386 if (1 >= private_empty.size()) 387 ; 388 if (!private_empty.size()) 389 ; 390 if (private_empty.size()) 391 ; 392 393 // Types with weird size() return type. 394 BoolSize bs; 395 if (bs.size() == 0) 396 ; 397 EnumSize es; 398 if (es.size() == 0) 399 ; 400 401 Derived derived; 402 if (derived.size() == 0) 403 ; 404 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 405 // CHECK-FIXES: {{^ }}if (derived.empty()){{$}} 406 if (derived == Derived()) 407 ; 408 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 409 // CHECK-FIXES: {{^ }}if (derived.empty()){{$}} 410 411 takesBool(derived.size()); 412 // CHECK-MESSAGES: :[[@LINE-1]]:13: warning: the 'empty' method should be used 413 // CHECK-FIXES: {{^ }}takesBool(!derived.empty()); 414 415 takesBool(derived.size() == 0); 416 // CHECK-MESSAGES: :[[@LINE-1]]:13: warning: the 'empty' method should be used 417 // CHECK-FIXES: {{^ }}takesBool(derived.empty()); 418 419 takesBool(derived.size() != 0); 420 // CHECK-MESSAGES: :[[@LINE-1]]:13: warning: the 'empty' method should be used 421 // CHECK-FIXES: {{^ }}takesBool(!derived.empty()); 422 423 bool b1 = derived.size(); 424 // CHECK-MESSAGES: :[[@LINE-1]]:13: warning: the 'empty' method should be used 425 // CHECK-FIXES: {{^ }}bool b1 = !derived.empty(); 426 427 bool b2(derived.size()); 428 // CHECK-MESSAGES: :[[@LINE-1]]:11: warning: the 'empty' method should be used 429 // CHECK-FIXES: {{^ }}bool b2(!derived.empty()); 430 431 auto b3 = static_cast<bool>(derived.size()); 432 // CHECK-MESSAGES: :[[@LINE-1]]:31: warning: the 'empty' method should be used 433 // CHECK-FIXES: {{^ }}auto b3 = static_cast<bool>(!derived.empty()); 434 435 auto b4 = (bool)derived.size(); 436 // CHECK-MESSAGES: :[[@LINE-1]]:19: warning: the 'empty' method should be used 437 // CHECK-FIXES: {{^ }}auto b4 = (bool)!derived.empty(); 438 439 auto b5 = bool(derived.size()); 440 // CHECK-MESSAGES: :[[@LINE-1]]:18: warning: the 'empty' method should be used 441 // CHECK-FIXES: {{^ }}auto b5 = bool(!derived.empty()); 442 443 return derived.size(); 444 // CHECK-MESSAGES: :[[@LINE-1]]:10: warning: the 'empty' method should be used 445 // CHECK-FIXES: {{^ }}return !derived.empty(); 446 } 447 448 class ConstructWithBoolField { 449 bool B; 450 public: ConstructWithBoolField(const std::vector<int> & C)451 ConstructWithBoolField(const std::vector<int> &C) : B(C.size()) {} 452 // CHECK-MESSAGES: :[[@LINE-1]]:57: warning: the 'empty' method should be used 453 // CHECK-MESSAGES: :9:8: note: method 'vector'::empty() defined here 454 // CHECK-FIXES: {{^ }}ConstructWithBoolField(const std::vector<int> &C) : B(!C.empty()) {} 455 }; 456 457 struct StructWithNSDMI { 458 std::vector<int> C; 459 bool B = C.size(); 460 // CHECK-MESSAGES: :[[@LINE-1]]:12: warning: the 'empty' method should be used 461 // CHECK-MESSAGES: :9:8: note: method 'vector'::empty() defined here 462 // CHECK-FIXES: {{^ }}bool B = !C.empty(); 463 }; 464 func(const std::vector<int> & C)465int func(const std::vector<int> &C) { 466 return C.size() ? 0 : 1; 467 // CHECK-MESSAGES: :[[@LINE-1]]:10: warning: the 'empty' method should be used 468 // CHECK-MESSAGES: :9:8: note: method 'vector'::empty() defined here 469 // CHECK-FIXES: {{^ }}return !C.empty() ? 0 : 1; 470 } 471 472 constexpr Lazy L; 473 static_assert(!L.size(), ""); 474 // CHECK-MESSAGES: :[[@LINE-1]]:16: warning: the 'empty' method should be used 475 // CHECK-MESSAGES: :101:18: note: method 'Lazy'::empty() defined here 476 // CHECK-FIXES: {{^}}static_assert(L.empty(), ""); 477 478 struct StructWithLazyNoexcept { 479 void func() noexcept(L.size()); 480 }; 481 482 #define CHECKSIZE(x) if (x.size()) {} 483 // CHECK-FIXES: #define CHECKSIZE(x) if (x.size()) {} 484 f()485template <typename T> void f() { 486 std::vector<T> v; 487 if (v.size()) 488 ; 489 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used to check for emptiness instead of 'size' [readability-container-size-empty] 490 // CHECK-MESSAGES: :9:8: note: method 'vector'::empty() defined here 491 // CHECK-FIXES: {{^ }}if (!v.empty()){{$}} 492 if (v == std::vector<T>()) 493 ; 494 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used to check for emptiness instead of comparing to an empty object [readability-container-size-empty] 495 // CHECK-FIXES: {{^ }}if (v.empty()){{$}} 496 // CHECK-FIXES-NEXT: ; 497 CHECKSIZE(v); 498 // CHECK-MESSAGES: :[[@LINE-1]]:13: warning: the 'empty' method should be used 499 // CHECK-MESSAGES: :9:8: note: method 'vector'::empty() defined here 500 // CHECK-FIXES: CHECKSIZE(v); 501 502 TemplatedContainer<T> templated_container; 503 if (templated_container.size()) 504 ; 505 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 506 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 507 // CHECK-FIXES: {{^ }}if (!templated_container.empty()){{$}} 508 if (templated_container != TemplatedContainer<T>()) 509 ; 510 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 511 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 512 // CHECK-FIXES: {{^ }}if (!templated_container.empty()){{$}} 513 // CHECK-FIXES-NEXT: ; 514 CHECKSIZE(templated_container); 515 // CHECK-MESSAGES: :[[@LINE-1]]:13: warning: the 'empty' method should be used 516 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 517 // CHECK-FIXES: CHECKSIZE(templated_container); 518 } 519 g()520void g() { 521 f<int>(); 522 f<double>(); 523 f<char *>(); 524 } 525 526 template <typename T> neverInstantiatedTemplate()527bool neverInstantiatedTemplate() { 528 std::vector<T> v; 529 if (v.size()) 530 ; 531 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used to check for emptiness instead of 'size' [readability-container-size-empty] 532 // CHECK-MESSAGES: :9:8: note: method 'vector'::empty() defined here 533 // CHECK-FIXES: {{^ }}if (!v.empty()){{$}} 534 535 if (v == std::vector<T>()) 536 ; 537 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used to check for emptiness instead of comparing to an empty object [readability-container-size-empty] 538 // CHECK-FIXES: {{^ }}if (v.empty()){{$}} 539 // CHECK-FIXES-NEXT: ; 540 if (v.size() == 0) 541 ; 542 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used to check for emptiness instead of 'size' [readability-container-size-empty] 543 // CHECK-MESSAGES: :9:8: note: method 'vector'::empty() defined here 544 // CHECK-FIXES: {{^ }}if (v.empty()){{$}} 545 if (v.size() != 0) 546 ; 547 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used to check for emptiness instead of 'size' [readability-container-size-empty] 548 // CHECK-MESSAGES: :9:8: note: method 'vector'::empty() defined here 549 // CHECK-FIXES: {{^ }}if (!v.empty()){{$}} 550 if (v.size() < 1) 551 ; 552 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used to check for emptiness instead of 'size' [readability-container-size-empty] 553 // CHECK-MESSAGES: :9:8: note: method 'vector'::empty() defined here 554 // CHECK-FIXES: {{^ }}if (v.empty()){{$}} 555 if (v.size() > 0) 556 ; 557 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used to check for emptiness instead of 'size' [readability-container-size-empty] 558 // CHECK-MESSAGES: :9:8: note: method 'vector'::empty() defined here 559 // CHECK-FIXES: {{^ }}if (!v.empty()){{$}} 560 if (v.size() == 1) 561 ; 562 if (v.size() != 1) 563 ; 564 if (v.size() == 2) 565 ; 566 if (v.size() != 2) 567 ; 568 569 if (static_cast<bool>(v.size())) 570 ; 571 // CHECK-MESSAGES: :[[@LINE-2]]:25: warning: the 'empty' method should be used to check for emptiness instead of 'size' [readability-container-size-empty] 572 // CHECK-MESSAGES: :9:8: note: method 'vector'::empty() defined here 573 // CHECK-FIXES: {{^ }}if (static_cast<bool>(!v.empty())){{$}} 574 if (v.size() && false) 575 ; 576 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used to check for emptiness instead of 'size' [readability-container-size-empty] 577 // CHECK-MESSAGES: :9:8: note: method 'vector'::empty() defined here 578 // CHECK-FIXES: {{^ }}if (!v.empty() && false){{$}} 579 if (!v.size()) 580 ; 581 // CHECK-MESSAGES: :[[@LINE-2]]:8: warning: the 'empty' method should be used to check for emptiness instead of 'size' [readability-container-size-empty] 582 // CHECK-MESSAGES: :9:8: note: method 'vector'::empty() defined here 583 // CHECK-FIXES: {{^ }}if (v.empty()){{$}} 584 585 TemplatedContainer<T> templated_container; 586 if (templated_container.size()) 587 ; 588 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 589 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 590 // CHECK-FIXES: {{^ }}if (!templated_container.empty()){{$}} 591 if (templated_container != TemplatedContainer<T>()) 592 ; 593 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: the 'empty' method should be used 594 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 595 // CHECK-FIXES: {{^ }}if (!templated_container.empty()){{$}} 596 // CHECK-FIXES-NEXT: ; 597 while (templated_container.size()) 598 ; 599 // CHECK-MESSAGES: :[[@LINE-2]]:10: warning: the 'empty' method should be used 600 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 601 // CHECK-FIXES: {{^ }}while (!templated_container.empty()){{$}} 602 603 do { 604 } 605 while (templated_container.size()); 606 // CHECK-MESSAGES: :[[@LINE-1]]:10: warning: the 'empty' method should be used 607 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 608 // CHECK-FIXES: {{^ }}while (!templated_container.empty()); 609 610 for (; templated_container.size();) 611 ; 612 // CHECK-MESSAGES: :[[@LINE-2]]:10: warning: the 'empty' method should be used 613 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 614 // CHECK-FIXES: {{^ }}for (; !templated_container.empty();){{$}} 615 616 if (true && templated_container.size()) 617 ; 618 // CHECK-MESSAGES: :[[@LINE-2]]:15: warning: the 'empty' method should be used 619 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 620 // CHECK-FIXES: {{^ }}if (true && !templated_container.empty()){{$}} 621 622 if (true || templated_container.size()) 623 ; 624 // CHECK-MESSAGES: :[[@LINE-2]]:15: warning: the 'empty' method should be used 625 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 626 // CHECK-FIXES: {{^ }}if (true || !templated_container.empty()){{$}} 627 628 if (!templated_container.size()) 629 ; 630 // CHECK-MESSAGES: :[[@LINE-2]]:8: warning: the 'empty' method should be used 631 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 632 // CHECK-FIXES: {{^ }}if (templated_container.empty()){{$}} 633 634 bool b1 = templated_container.size(); 635 // CHECK-MESSAGES: :[[@LINE-1]]:13: warning: the 'empty' method should be used 636 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 637 // CHECK-FIXES: {{^ }}bool b1 = !templated_container.empty(); 638 639 bool b2(templated_container.size()); 640 // CHECK-MESSAGES: :[[@LINE-1]]:11: warning: the 'empty' method should be used 641 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 642 // CHECK-FIXES: {{^ }}bool b2(!templated_container.empty()); 643 644 auto b3 = static_cast<bool>(templated_container.size()); 645 // CHECK-MESSAGES: :[[@LINE-1]]:31: warning: the 'empty' method should be used 646 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 647 // CHECK-FIXES: {{^ }}auto b3 = static_cast<bool>(!templated_container.empty()); 648 649 auto b4 = (bool)templated_container.size(); 650 // CHECK-MESSAGES: :[[@LINE-1]]:19: warning: the 'empty' method should be used 651 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 652 // CHECK-FIXES: {{^ }}auto b4 = (bool)!templated_container.empty(); 653 654 auto b5 = bool(templated_container.size()); 655 // CHECK-MESSAGES: :[[@LINE-1]]:18: warning: the 'empty' method should be used 656 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 657 // CHECK-FIXES: {{^ }}auto b5 = bool(!templated_container.empty()); 658 659 takesBool(templated_container.size()); 660 // We don't detect this one because we don't know the parameter of takesBool 661 // until the type of templated_container.size() is known 662 663 return templated_container.size(); 664 // CHECK-MESSAGES: :[[@LINE-1]]:10: warning: the 'empty' method should be used 665 // CHECK-MESSAGES: :44:8: note: method 'TemplatedContainer'::empty() defined here 666 // CHECK-FIXES: {{^ }}return !templated_container.empty(); 667 } 668 669 template <typename TypeRequiresSize> instantiatedTemplateWithSizeCall()670void instantiatedTemplateWithSizeCall() { 671 TypeRequiresSize t; 672 // The instantiation of the template with std::vector<int> should not 673 // result in changing the template, because we don't know that 674 // TypeRequiresSize generally has `.empty()` 675 if (t.size()) 676 ; 677 678 if (t == TypeRequiresSize{}) 679 ; 680 681 if (t != TypeRequiresSize{}) 682 ; 683 } 684 685 class TypeWithSize { 686 public: 687 TypeWithSize(); 688 bool operator==(const TypeWithSize &other) const; 689 bool operator!=(const TypeWithSize &other) const; 690 size() const691 unsigned size() const { return 0; } 692 // Does not have `.empty()` 693 }; 694 instantiator()695void instantiator() { 696 instantiatedTemplateWithSizeCall<TypeWithSize>(); 697 instantiatedTemplateWithSizeCall<std::vector<int>>(); 698 } 699