mirror of
https://github.com/GothenburgBitFactory/taskwarrior.git
synced 2025-07-31 17:03:30 +02:00
Enhancement - caseless find
- Added support for a starting offset.
This commit is contained in:
parent
2dfe144236
commit
06ecef76d3
3 changed files with 52 additions and 1 deletions
|
@ -34,7 +34,7 @@ Context context;
|
|||
////////////////////////////////////////////////////////////////////////////////
|
||||
int main (int argc, char** argv)
|
||||
{
|
||||
UnitTest t (176);
|
||||
UnitTest t (178);
|
||||
|
||||
// void wrapText (std::vector <std::string>& lines, const std::string& text, const int width)
|
||||
std::string text = "This is a test of the line wrapping code.";
|
||||
|
@ -356,6 +356,9 @@ int main (int argc, char** argv)
|
|||
t.is ((int) find ("FOO", "fo", false), 0, "FOO contains fo (caseless)");
|
||||
t.is ((int) find ("FOO", "FO", false), 0, "FOO contains FO (caseless)");
|
||||
|
||||
// Test start offset.
|
||||
t.is ((int) find ("one two three", "e", 3, true), (int) 11, "offset obeyed");
|
||||
t.is ((int) find ("one two three", "e", 11, true), (int) 11, "offset obeyed");
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
47
src/text.cpp
47
src/text.cpp
|
@ -519,3 +519,50 @@ std::string::size_type find (
|
|||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
std::string::size_type find (
|
||||
const std::string& text,
|
||||
const std::string& pattern,
|
||||
std::string::size_type begin,
|
||||
bool sensitive /*= true*/)
|
||||
{
|
||||
// Implement a sensitive find, which is really just a loop withing a loop,
|
||||
// comparing lower-case versions of each character in turn.
|
||||
if (!sensitive)
|
||||
{
|
||||
// Handle empty pattern.
|
||||
const char* p = pattern.c_str ();
|
||||
size_t len = pattern.length ();
|
||||
if (len == 0)
|
||||
return 0;
|
||||
|
||||
// Handle bad begin.
|
||||
if (begin >= len)
|
||||
return std::string::npos;
|
||||
|
||||
// Evaluate these once, for performance reasons.
|
||||
const char* t = text.c_str ();
|
||||
const char* start = t + begin;
|
||||
const char* end = start + text.size ();
|
||||
|
||||
for (; t < end - len; ++t)
|
||||
{
|
||||
int diff;
|
||||
for (size_t i = 0; i < len; ++i)
|
||||
if ((diff = tolower (t[i]) - tolower (p[i])))
|
||||
break;
|
||||
|
||||
// diff == 0 means there was no break from the loop, which only occurs
|
||||
// when a difference is detected. Therefore, the loop terminated, and
|
||||
// diff is zero.
|
||||
if (diff == 0)
|
||||
return t - start;
|
||||
}
|
||||
|
||||
return std::string::npos;
|
||||
}
|
||||
|
||||
// Otherwise, just use std::string::find.
|
||||
return text.find (pattern, begin);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
|
|
@ -56,6 +56,7 @@ bool isWordStart (const std::string&, std::string::size_type);
|
|||
bool isWordEnd (const std::string&, std::string::size_type);
|
||||
bool compare (const std::string&, const std::string&, bool sensitive = true);
|
||||
std::string::size_type find (const std::string&, const std::string&, bool sensitive = true);
|
||||
std::string::size_type find (const std::string&, const std::string&, std::string::size_type, bool sensitive = true);
|
||||
|
||||
#endif
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue