| 404 | } |
| 405 | |
| 406 | absl::optional<int64_t> StringValue::LastIndexOf( |
| 407 | absl::string_view string) const { |
| 408 | return value_.Visit(absl::Overload( |
| 409 | [&](absl::string_view lhs) -> absl::optional<int64_t> { |
| 410 | int64_t last_index = -1; |
| 411 | int64_t code_points = 0; |
| 412 | while (lhs.size() >= string.size()) { |
| 413 | if (absl::StartsWith(lhs, string)) { |
| 414 | last_index = code_points; |
| 415 | } |
| 416 | if (lhs.size() == string.size()) { |
| 417 | break; |
| 418 | } |
| 419 | size_t code_units = |
| 420 | cel::internal::Utf8Decode(lhs, /*code_point=*/nullptr); |
| 421 | lhs.remove_prefix(code_units); |
| 422 | ++code_points; |
| 423 | } |
| 424 | if (last_index < 0) return absl::nullopt; |
| 425 | return last_index; |
| 426 | }, |
| 427 | [&](absl::Cord lhs) -> absl::optional<int64_t> { |
| 428 | int64_t last_index = -1; |
| 429 | int64_t code_points = 0; |
| 430 | while (lhs.size() >= string.size()) { |
| 431 | if (lhs.StartsWith(string)) { |
| 432 | last_index = code_points; |
| 433 | } |
| 434 | if (lhs.size() == string.size()) { |
| 435 | break; |
| 436 | } |
| 437 | size_t code_units = cel::internal::Utf8Decode(lhs.char_begin(), |
| 438 | /*code_point=*/nullptr); |
| 439 | lhs.RemovePrefix(code_units); |
| 440 | ++code_points; |
| 441 | } |
| 442 | if (last_index < 0) return absl::nullopt; |
| 443 | return last_index; |
| 444 | })); |
| 445 | } |
| 446 | |
| 447 | absl::optional<int64_t> StringValue::LastIndexOf( |
| 448 | const absl::Cord& string) const { |