string escaping support functions

the split function now takes an additional escape parameter and
does not split on separators that have the escaper before it.

An utility escape function that adds escape before separators
is also added.
This commit is contained in:
Maxime Coste 2013-07-24 22:37:17 +02:00
parent d6425f1d50
commit b5db256384
3 changed files with 43 additions and 10 deletions

View File

@ -5,7 +5,7 @@
namespace Kakoune namespace Kakoune
{ {
std::vector<String> split(const String& str, char separator) std::vector<String> split(const String& str, char separator, char escape)
{ {
auto begin = str.begin(); auto begin = str.begin();
auto end = str.begin(); auto end = str.begin();
@ -13,12 +13,40 @@ std::vector<String> split(const String& str, char separator)
std::vector<String> res; std::vector<String> res;
while (end != str.end()) while (end != str.end())
{ {
while (end != str.end() and *end != separator) res.emplace_back();
String& element = res.back();
while (end != str.end())
{
auto c = *end;
if (c == escape and end + 1 != end and *(end+1) == separator)
{
element += separator;
end += 2;
}
else if (c == separator)
{
++end; ++end;
res.push_back(String(begin, end));
if (end == str.end())
break; break;
begin = ++end; }
else
{
element += c;
++end;
}
}
begin = end;
}
return res;
}
String escape(const String& str, char character, char escape)
{
String res;
for (auto& c : str)
{
if (c == character)
res += escape;
res += c;
} }
return res; return res;
} }

View File

@ -84,7 +84,8 @@ inline String operator+(Codepoint lhs, const String& rhs)
return String(lhs) + rhs; return String(lhs) + rhs;
} }
std::vector<String> split(const String& str, char separator); std::vector<String> split(const String& str, char separator, char escape = 0);
String escape(const String& str, char character, char escape);
inline String operator"" _str(const char* str, size_t) inline String operator"" _str(const char* str, size_t)
{ {

View File

@ -120,11 +120,15 @@ void test_string()
{ {
kak_assert(String("youpi ") + "matin" == "youpi matin"); kak_assert(String("youpi ") + "matin" == "youpi matin");
std::vector<String> splited = split("youpi:matin::tchou", ':'); std::vector<String> splited = split("youpi:matin::tchou\\:kanaky:hihi\\:", ':', '\\');
kak_assert(splited[0] == "youpi"); kak_assert(splited[0] == "youpi");
kak_assert(splited[1] == "matin"); kak_assert(splited[1] == "matin");
kak_assert(splited[2] == ""); kak_assert(splited[2] == "");
kak_assert(splited[3] == "tchou"); kak_assert(splited[3] == "tchou:kanaky");
kak_assert(splited[4] == "hihi:");
String escaped = escape("youpi:matin:tchou:", ':', '\\');
kak_assert(escaped == "youpi\\:matin\\:tchou\\:");
} }
void test_keys() void test_keys()