//
// Copyright 2017 The Abseil Authors.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//      https://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
// -----------------------------------------------------------------------------
// File: str_split.h
// -----------------------------------------------------------------------------
//
// This file contains functions for splitting strings. It defines the main
// `StrSplit()` function, several delimiters for determining the boundaries on
// which to split the string, and predicates for filtering delimited results.
// `StrSplit()` adapts the returned collection to the type specified by the
// caller.
//
// Example:
//
//   // Splits the given string on commas. Returns the results in a
//   // vector of strings.
//   std::vector<std::string> v = absl::StrSplit("a,b,c", ',');
//   // Can also use ","
//   // v[0] == "a", v[1] == "b", v[2] == "c"
//
// See StrSplit() below for more information.
#ifndef ABSL_STRINGS_STR_SPLIT_H_
#define ABSL_STRINGS_STR_SPLIT_H_

#include <algorithm>
#include <cstddef>
#include <map>
#include <set>
#include <string>
#include <utility>
#include <vector>

#include "absl/base/internal/raw_logging.h"
#include "absl/base/macros.h"
#include "absl/strings/internal/str_split_internal.h"
#include "absl/strings/string_view.h"
#include "absl/strings/strip.h"

namespace absl {
ABSL_NAMESPACE_BEGIN

//------------------------------------------------------------------------------
// Delimiters
//------------------------------------------------------------------------------
//
// `StrSplit()` uses delimiters to define the boundaries between elements in the
// provided input. Several `Delimiter` types are defined below. If a string
// (`const char*`, `std::string`, or `absl::string_view`) is passed in place of
// an explicit `Delimiter` object, `StrSplit()` treats it the same way as if it
// were passed a `ByString` delimiter.
//
// A `Delimiter` is an object with a `Find()` function that knows how to find
// the first occurrence of itself in a given `absl::string_view`.
//
// The following `Delimiter` types are available for use within `StrSplit()`:
//
//   - `ByString` (default for string arguments)
//   - `ByChar` (default for a char argument)
//   - `ByAnyChar`
//   - `ByLength`
//   - `MaxSplits`
//
// A Delimiter's `Find()` member function will be passed an input `text` that is
// to be split and a position (`pos`) to begin searching for the next delimiter
// in `text`. The returned absl::string_view should refer to the next occurrence
// (after `pos`) of the represented delimiter; this returned absl::string_view
// represents the next location where the input `text` should be broken.
//
// The returned absl::string_view may be zero-length if the Delimiter does not
// represent a part of the string (e.g., a fixed-length delimiter). If no
// delimiter is found in the input `text`, a zero-length absl::string_view
// referring to `text.end()` should be returned (e.g.,
// `text.substr(text.size())`). It is important that the returned
// absl::string_view always be within the bounds of the input `text` given as an
// argument--it must not refer to a string that is physically located outside of
// the given string.
//
// The following example is a simple Delimiter object that is created with a
// single char and will look for that char in the text passed to the `Find()`
// function:
//
//   struct SimpleDelimiter {
//     const char c_;
//     explicit SimpleDelimiter(char c) : c_(c) {}
//     absl::string_view Find(absl::string_view text, size_t pos) {
//       auto found = text.find(c_, pos);
//       if (found == absl::string_view::npos)
//         return text.substr(text.size());
//
//       return text.substr(found, 1);
//     }
//   };

// ByString
//
// A sub-string delimiter. If `StrSplit()` is passed a string in place of a
// `Delimiter` object, the string will be implicitly converted into a
// `ByString` delimiter.
//
// Example:
//
//   // Because a string literal is converted to an `absl::ByString`,
//   // the following two splits are equivalent.
//
//   std::vector<std::string> v1 = absl::StrSplit("a, b, c", ", ");
//
//   using absl::ByString;
//   std::vector<std::string> v2 = absl::StrSplit("a, b, c",
//                                                ByString(", "));
//   // v[0] == "a", v[1] == "b", v[2] == "c"
class ByString {
 public:
  explicit ByString(absl::string_view sp);
  absl::string_view Find(absl::string_view text, size_t pos) const;

 private:
  std::string delimiter_;
};

// ByAsciiWhitespace
//
// A sub-string delimiter that splits by ASCII whitespace
// (space, tab, vertical tab, formfeed, linefeed, or carriage return).
// Note: you probably want to use absl::SkipEmpty() as well!
//
// This class is equivalent to ByAnyChar with ASCII whitespace chars.
//
// Example:
//
//   std::vector<std::string> v = absl::StrSplit(
//       "a b\tc\n  d  \n", absl::ByAsciiWhitespace(), absl::SkipEmpty());
//   // v[0] == "a", v[1] == "b", v[2] == "c", v[3] == "d"
class ByAsciiWhitespace {
 public:
  absl::string_view Find(absl::string_view text, size_t pos) const;
};

// ByChar
//
// A single character delimiter. `ByChar` is functionally equivalent to a
// 1-char string within a `ByString` delimiter, but slightly more efficient.
//
// Example:
//
//   // Because a char literal is converted to a absl::ByChar,
//   // the following two splits are equivalent.
//   std::vector<std::string> v1 = absl::StrSplit("a,b,c", ',');
//   using absl::ByChar;
//   std::vector<std::string> v2 = absl::StrSplit("a,b,c", ByChar(','));
//   // v[0] == "a", v[1] == "b", v[2] == "c"
//
// `ByChar` is also the default delimiter if a single character is given
// as the delimiter to `StrSplit()`. For example, the following calls are
// equivalent:
//
//   std::vector<std::string> v = absl::StrSplit("a-b", '-');
//
//   using absl::ByChar;
//   std::vector<std::string> v = absl::StrSplit("a-b", ByChar('-'));
//
class ByChar {
 public:
  explicit ByChar(char c) : c_(c) {}
  absl::string_view Find(absl::string_view text, size_t pos) const;

 private:
  char c_;
};

// ByAnyChar
//
// A delimiter that will match any of the given byte-sized characters within
// its provided string.
//
// Note: this delimiter works with single-byte string data, but does not work
// with variable-width encodings, such as UTF-8.
//
// Example:
//
//   using absl::ByAnyChar;
//   std::vector<std::string> v = absl::StrSplit("a,b=c", ByAnyChar(",="));
//   // v[0] == "a", v[1] == "b", v[2] == "c"
//
// If `ByAnyChar` is given the empty string, it behaves exactly like
// `ByString` and matches each individual character in the input string.
//
class ByAnyChar {
 public:
  explicit ByAnyChar(absl::string_view sp);
  absl::string_view Find(absl::string_view text, size_t pos) const;

 private:
  const std::string delimiters_;
};

// ByLength
//
// A delimiter for splitting into equal-length strings. The length argument to
// the constructor must be greater than 0.
//
// Note: this delimiter works with single-byte string data, but does not work
// with variable-width encodings, such as UTF-8.
//
// Example:
//
//   using absl::ByLength;
//   std::vector<std::string> v = absl::StrSplit("123456789", ByLength(3));

//   // v[0] == "123", v[1] == "456", v[2] == "789"
//
// Note that the string does not have to be a multiple of the fixed split
// length. In such a case, the last substring will be shorter.
//
//   using absl::ByLength;
//   std::vector<std::string> v = absl::StrSplit("12345", ByLength(2));
//
//   // v[0] == "12", v[1] == "34", v[2] == "5"
class ByLength {
 public:
  explicit ByLength(ptrdiff_t length);
  absl::string_view Find(absl::string_view text, size_t pos) const;

 private:
  const ptrdiff_t length_;
};

namespace strings_internal {

// A traits-like metafunction for selecting the default Delimiter object type
// for a particular Delimiter type. The base case simply exposes type Delimiter
// itself as the delimiter's Type. However, there are specializations for
// string-like objects that map them to the ByString delimiter object.
// This allows functions like absl::StrSplit() and absl::MaxSplits() to accept
// string-like objects (e.g., ',') as delimiter arguments but they will be
// treated as if a ByString delimiter was given.
template <typename Delimiter>
struct SelectDelimiter {
  using type = Delimiter;
};

template <>
struct SelectDelimiter<char> {
  using type = ByChar;
};
template <>
struct SelectDelimiter<char*> {
  using type = ByString;
};
template <>
struct SelectDelimiter<const char*> {
  using type = ByString;
};
template <>
struct SelectDelimiter<absl::string_view> {
  using type = ByString;
};
template <>
struct SelectDelimiter<std::string> {
  using type = ByString;
};

// Wraps another delimiter and sets a max number of matches for that delimiter.
template <typename Delimiter>
class MaxSplitsImpl {
 public:
  MaxSplitsImpl(Delimiter delimiter, int limit)
      : delimiter_(std::move(delimiter)), limit_(limit), count_(0) {}
  absl::string_view Find(absl::string_view text, size_t pos) {
    if (count_++ == limit_) {
      return absl::string_view(text.data() + text.size(),
                               0);  // No more matches.
    }
    return delimiter_.Find(text, pos);
  }

 private:
  Delimiter delimiter_;
  const int limit_;
  int count_;
};

}  // namespace strings_internal

// MaxSplits()
//
// A delimiter that limits the number of matches which can occur to the passed
// `limit`. The last element in the returned collection will contain all
// remaining unsplit pieces, which may contain instances of the delimiter.
// The collection will contain at most `limit` + 1 elements.
// Example:
//
//   using absl::MaxSplits;
//   std::vector<std::string> v = absl::StrSplit("a,b,c", MaxSplits(',', 1));
//
//   // v[0] == "a", v[1] == "b,c"
template <typename Delimiter>
inline strings_internal::MaxSplitsImpl<
    typename strings_internal::SelectDelimiter<Delimiter>::type>
MaxSplits(Delimiter delimiter, int limit) {
  typedef
      typename strings_internal::SelectDelimiter<Delimiter>::type DelimiterType;
  return strings_internal::MaxSplitsImpl<DelimiterType>(
      DelimiterType(delimiter), limit);
}

//------------------------------------------------------------------------------
// Predicates
//------------------------------------------------------------------------------
//
// Predicates filter the results of a `StrSplit()` by determining whether or not
// a resultant element is included in the result set. A predicate may be passed
// as an optional third argument to the `StrSplit()` function.
//
// Predicates are unary functions (or functors) that take a single
// `absl::string_view` argument and return a bool indicating whether the
// argument should be included (`true`) or excluded (`false`).
//
// Predicates are useful when filtering out empty substrings. By default, empty
// substrings may be returned by `StrSplit()`, which is similar to the way split
// functions work in other programming languages.

// AllowEmpty()
//
// Always returns `true`, indicating that all strings--including empty
// strings--should be included in the split output. This predicate is not
// strictly needed because this is the default behavior of `StrSplit()`;
// however, it might be useful at some call sites to make the intent explicit.
//
// Example:
//
//  std::vector<std::string> v = absl::StrSplit(" a , ,,b,", ',', AllowEmpty());
//
//  // v[0] == " a ", v[1] == " ", v[2] == "", v[3] = "b", v[4] == ""
struct AllowEmpty {
  bool operator()(absl::string_view) const { return true; }
};

// SkipEmpty()
//
// Returns `false` if the given `absl::string_view` is empty, indicating that
// `StrSplit()` should omit the empty string.
//
// Example:
//
//   std::vector<std::string> v = absl::StrSplit(",a,,b,", ',', SkipEmpty());
//
//   // v[0] == "a", v[1] == "b"
//
// Note: `SkipEmpty()` does not consider a string containing only whitespace
// to be empty. To skip such whitespace as well, use the `SkipWhitespace()`
// predicate.
struct SkipEmpty {
  bool operator()(absl::string_view sp) const { return !sp.empty(); }
};

// SkipWhitespace()
//
// Returns `false` if the given `absl::string_view` is empty *or* contains only
// whitespace, indicating that `StrSplit()` should omit the string.
//
// Example:
//
//   std::vector<std::string> v = absl::StrSplit(" a , ,,b,",
//                                               ',', SkipWhitespace());
//   // v[0] == " a ", v[1] == "b"
//
//   // SkipEmpty() would return whitespace elements
//   std::vector<std::string> v = absl::StrSplit(" a , ,,b,", ',', SkipEmpty());
//   // v[0] == " a ", v[1] == " ", v[2] == "b"
struct SkipWhitespace {
  bool operator()(absl::string_view sp) const {
    sp = absl::StripAsciiWhitespace(sp);
    return !sp.empty();
  }
};

template <typename T>
using EnableSplitIfString =
    typename std::enable_if<std::is_same<T, std::string>::value ||
                            std::is_same<T, const std::string>::value,
                            int>::type;

//------------------------------------------------------------------------------
//                                  StrSplit()
//------------------------------------------------------------------------------

// StrSplit()
//
// Splits a given string based on the provided `Delimiter` object, returning the
// elements within the type specified by the caller. Optionally, you may pass a
// `Predicate` to `StrSplit()` indicating whether to include or exclude the
// resulting element within the final result set. (See the overviews for
// Delimiters and Predicates above.)
//
// Example:
//
//   std::vector<std::string> v = absl::StrSplit("a,b,c,d", ',');
//   // v[0] == "a", v[1] == "b", v[2] == "c", v[3] == "d"
//
// You can also provide an explicit `Delimiter` object:
//
// Example:
//
//   using absl::ByAnyChar;
//   std::vector<std::string> v = absl::StrSplit("a,b=c", ByAnyChar(",="));
//   // v[0] == "a", v[1] == "b", v[2] == "c"
//
// See above for more information on delimiters.
//
// By default, empty strings are included in the result set. You can optionally
// include a third `Predicate` argument to apply a test for whether the
// resultant element should be included in the result set:
//
// Example:
//
//   std::vector<std::string> v = absl::StrSplit(" a , ,,b,",
//                                               ',', SkipWhitespace());
//   // v[0] == " a ", v[1] == "b"
//
// See above for more information on predicates.
//
//------------------------------------------------------------------------------
// StrSplit() Return Types
//------------------------------------------------------------------------------
//
// The `StrSplit()` function adapts the returned collection to the collection
// specified by the caller (e.g. `std::vector` above). The returned collections
// may contain `std::string`, `absl::string_view` (in which case the original
// string being split must ensure that it outlives the collection), or any
// object that can be explicitly created from an `absl::string_view`. This
// behavior works for:
//
// 1) All standard STL containers including `std::vector`, `std::list`,
//    `std::deque`, `std::set`,`std::multiset`, 'std::map`, and `std::multimap`.
// 2) `std::pair` (which is not actually a container). See below.
// 3) `std::array`, which is a container but has different behavior due to its
//    fixed size. See below.
//
// Example:
//
//   // The results are returned as `absl::string_view` objects. Note that we
//   // have to ensure that the input string outlives any results.
//   std::vector<absl::string_view> v = absl::StrSplit("a,b,c", ',');
//
//   // Stores results in a std::set<std::string>, which also performs
//   // de-duplication and orders the elements in ascending order.
//   std::set<std::string> a = absl::StrSplit("b,a,c,a,b", ',');
//   // a[0] == "a", a[1] == "b", a[2] == "c"
//
//   // `StrSplit()` can be used within a range-based for loop, in which case
//   // each element will be of type `absl::string_view`.
//   std::vector<std::string> v;
//   for (const auto sv : absl::StrSplit("a,b,c", ',')) {
//     if (sv != "b") v.emplace_back(sv);
//   }
//   // v[0] == "a", v[1] == "c"
//
//   // Stores results in a map. The map implementation assumes that the input
//   // is provided as a series of key/value pairs. For example, the 0th element
//   // resulting from the split will be stored as a key to the 1st element. If
//   // an odd number of elements are resolved, the last element is paired with
//   // a default-constructed value (e.g., empty string).
//   std::map<std::string, std::string> m = absl::StrSplit("a,b,c", ',');
//   // m["a"] == "b", m["c"] == ""     // last component value equals ""
//
// Splitting to `std::pair` is an interesting case because it can hold only two
// elements and is not a collection type. When splitting to a `std::pair` the
// first two split strings become the `std::pair` `.first` and `.second`
// members, respectively. The remaining split substrings are discarded. If there
// are less than two split substrings, the empty string is used for the
// corresponding `std::pair` member.
//
// Example:
//
//   // Stores first two split strings as the members in a std::pair.
//   std::pair<std::string, std::string> p = absl::StrSplit("a,b,c", ',');
//   // p.first == "a", p.second == "b"       // "c" is omitted.
//
//
// Splitting to `std::array` is similar to splitting to `std::pair`, but for
// N elements instead of two; missing elements are filled with the empty string
// and extra elements are discarded.
//
// Examples:
//
//   // Stores first two split strings as the elements in a std::array.
//   std::array<std::string, 2> a = absl::StrSplit("a,b,c", ',');
//   // a[0] == "a", a[1] == "b"   // "c" is omitted.
//
//   // The second element is empty.
//   std::array<std::string, 2> a = absl::StrSplit("a,", ',');
//   // a[0] == "a", a[1] == ""
//
// The `StrSplit()` function can be used multiple times to perform more
// complicated splitting logic, such as intelligently parsing key-value pairs.
//
// Example:
//
//   // The input string "a=b=c,d=e,f=,g" becomes
//   // { "a" => "b=c", "d" => "e", "f" => "", "g" => "" }
//   std::map<std::string, std::string> m;
//   for (absl::string_view sp : absl::StrSplit("a=b=c,d=e,f=,g", ',')) {
//     m.insert(absl::StrSplit(sp, absl::MaxSplits('=', 1)));
//   }
//   EXPECT_EQ("b=c", m.find("a")->second);
//   EXPECT_EQ("e", m.find("d")->second);
//   EXPECT_EQ("", m.find("f")->second);
//   EXPECT_EQ("", m.find("g")->second);
//
// WARNING: Due to a legacy bug that is maintained for backward compatibility,
// splitting the following empty string_views produces different results:
//
//   absl::StrSplit(absl::string_view(""), '-');  // {""}
//   absl::StrSplit(absl::string_view(), '-');    // {}, but should be {""}
//
// Try not to depend on this distinction because the bug may one day be fixed.
template <typename Delimiter>
strings_internal::Splitter<
    typename strings_internal::SelectDelimiter<Delimiter>::type, AllowEmpty,
    absl::string_view>
StrSplit(strings_internal::ConvertibleToStringView text, Delimiter d) {
  using DelimiterType =
      typename strings_internal::SelectDelimiter<Delimiter>::type;
  return strings_internal::Splitter<DelimiterType, AllowEmpty,
                                    absl::string_view>(
      text.value(), DelimiterType(d), AllowEmpty());
}

template <typename Delimiter, typename StringType,
          EnableSplitIfString<StringType> = 0>
strings_internal::Splitter<
    typename strings_internal::SelectDelimiter<Delimiter>::type, AllowEmpty,
    std::string>
StrSplit(StringType&& text, Delimiter d) {
  using DelimiterType =
      typename strings_internal::SelectDelimiter<Delimiter>::type;
  return strings_internal::Splitter<DelimiterType, AllowEmpty, std::string>(
      std::move(text), DelimiterType(d), AllowEmpty());
}

template <typename Delimiter, typename Predicate>
strings_internal::Splitter<
    typename strings_internal::SelectDelimiter<Delimiter>::type, Predicate,
    absl::string_view>
StrSplit(strings_internal::ConvertibleToStringView text, Delimiter d,
         Predicate p) {
  using DelimiterType =
      typename strings_internal::SelectDelimiter<Delimiter>::type;
  return strings_internal::Splitter<DelimiterType, Predicate,
                                    absl::string_view>(
      text.value(), DelimiterType(std::move(d)), std::move(p));
}

template <typename Delimiter, typename Predicate, typename StringType,
          EnableSplitIfString<StringType> = 0>
strings_internal::Splitter<
    typename strings_internal::SelectDelimiter<Delimiter>::type, Predicate,
    std::string>
StrSplit(StringType&& text, Delimiter d, Predicate p) {
  using DelimiterType =
      typename strings_internal::SelectDelimiter<Delimiter>::type;
  return strings_internal::Splitter<DelimiterType, Predicate, std::string>(
      std::move(text), DelimiterType(d), std::move(p));
}

ABSL_NAMESPACE_END
}  // namespace absl

#endif  // ABSL_STRINGS_STR_SPLIT_H_
