do not copy strings while doing case insensitive comparison
This commit is contained in:
@@ -225,32 +225,6 @@ void ParseArgv(int argc, char **argv)
|
|||||||
exit(0);
|
exit(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool CaseInsensitiveSorting::operator()(std::string a, std::string b)
|
|
||||||
{
|
|
||||||
ToLower(a);
|
|
||||||
ToLower(b);
|
|
||||||
if (Config.ignore_leading_the)
|
|
||||||
{
|
|
||||||
RemoveTheWord(a);
|
|
||||||
RemoveTheWord(b);
|
|
||||||
}
|
|
||||||
return a < b;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool CaseInsensitiveSorting::operator()(Song *sa, Song *sb)
|
|
||||||
{
|
|
||||||
std::string a = sa->GetName();
|
|
||||||
std::string b = sb->GetName();
|
|
||||||
ToLower(a);
|
|
||||||
ToLower(b);
|
|
||||||
if (Config.ignore_leading_the)
|
|
||||||
{
|
|
||||||
RemoveTheWord(a);
|
|
||||||
RemoveTheWord(b);
|
|
||||||
}
|
|
||||||
return a < b;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool CaseInsensitiveSorting::operator()(const Item &a, const Item &b)
|
bool CaseInsensitiveSorting::operator()(const Item &a, const Item &b)
|
||||||
{
|
{
|
||||||
if (a.type == b.type)
|
if (a.type == b.type)
|
||||||
@@ -258,9 +232,9 @@ bool CaseInsensitiveSorting::operator()(const Item &a, const Item &b)
|
|||||||
switch (a.type)
|
switch (a.type)
|
||||||
{
|
{
|
||||||
case itDirectory:
|
case itDirectory:
|
||||||
return operator()(ExtractTopDirectory(a.name), ExtractTopDirectory(b.name));
|
return cmp(ExtractTopDirectory(a.name), ExtractTopDirectory(b.name)) < 0;
|
||||||
case itPlaylist:
|
case itPlaylist:
|
||||||
return operator()(a.name, b.name);
|
return cmp(a.name, b.name) < 0;
|
||||||
case itSong:
|
case itSong:
|
||||||
return operator()(a.song, b.song);
|
return operator()(a.song, b.song);
|
||||||
default: // there's no other type, just silence compiler.
|
default: // there's no other type, just silence compiler.
|
||||||
@@ -354,13 +328,6 @@ std::string GetLineValue(std::string &line, char a, char b, bool once)
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
void RemoveTheWord(std::string &s)
|
|
||||||
{
|
|
||||||
size_t the_pos = s.find("the ");
|
|
||||||
if (the_pos == 0 && the_pos != std::string::npos)
|
|
||||||
s = s.substr(4);
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string ExtractTopDirectory(const std::string &s)
|
std::string ExtractTopDirectory(const std::string &s)
|
||||||
{
|
{
|
||||||
size_t slash = s.rfind("/");
|
size_t slash = s.rfind("/");
|
||||||
|
|||||||
@@ -30,21 +30,57 @@
|
|||||||
bool ConnectToMPD();
|
bool ConnectToMPD();
|
||||||
void ParseArgv(int, char **);
|
void ParseArgv(int, char **);
|
||||||
|
|
||||||
|
class CaseInsensitiveStringComparison
|
||||||
|
{
|
||||||
|
bool hasTheWord(const std::string &s)
|
||||||
|
{
|
||||||
|
return (s.length() > 3)
|
||||||
|
&& (s[0] == 't' || s[0] == 'T')
|
||||||
|
&& (s[1] == 'h' || s[1] == 'H')
|
||||||
|
&& (s[2] == 'e' || s[2] == 'E')
|
||||||
|
&& (s[3] == ' ');
|
||||||
|
}
|
||||||
|
|
||||||
|
public:
|
||||||
|
int operator()(const std::string &a, const std::string &b)
|
||||||
|
{
|
||||||
|
const char *i = a.c_str();
|
||||||
|
const char *j = b.c_str();
|
||||||
|
if (Config.ignore_leading_the)
|
||||||
|
{
|
||||||
|
if (hasTheWord(a))
|
||||||
|
i += 4;
|
||||||
|
if (hasTheWord(b))
|
||||||
|
j += 4;
|
||||||
|
}
|
||||||
|
int dist;
|
||||||
|
while (!(dist = tolower(*i)-tolower(*j)) && *j)
|
||||||
|
++i, ++j;
|
||||||
|
return dist;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
class CaseInsensitiveSorting
|
class CaseInsensitiveSorting
|
||||||
{
|
{
|
||||||
|
CaseInsensitiveStringComparison cmp;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
bool operator()(std::string, std::string);
|
bool operator()(const std::string &a, const std::string &b)
|
||||||
bool operator()(MPD::Song *, MPD::Song *);
|
{
|
||||||
bool operator()(const MPD::Item &, const MPD::Item &);
|
return cmp(a, b) < 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool operator()(MPD::Song *a, MPD::Song *b)
|
||||||
|
{
|
||||||
|
return cmp(a->GetName(), b->GetName()) < 0;
|
||||||
|
}
|
||||||
|
|
||||||
template <typename A, typename B> bool operator()(const std::pair<A, B> &a, const std::pair<A, B> &b)
|
template <typename A, typename B> bool operator()(const std::pair<A, B> &a, const std::pair<A, B> &b)
|
||||||
{
|
{
|
||||||
std::string aa = a.first;
|
return cmp(a.first, b.first) < 0;
|
||||||
std::string bb = b.first;
|
|
||||||
ToLower(aa);
|
|
||||||
ToLower(bb);
|
|
||||||
return aa < bb;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool operator()(const MPD::Item &, const MPD::Item &);
|
||||||
};
|
};
|
||||||
|
|
||||||
template <typename A, typename B> std::string StringPairToString(const std::pair<A, B> &pair, void *)
|
template <typename A, typename B> std::string StringPairToString(const std::pair<A, B> &pair, void *)
|
||||||
@@ -115,12 +151,10 @@ std::string FindSharedDir(Menu<MPD::Song> *);
|
|||||||
std::string FindSharedDir(const MPD::SongList &);
|
std::string FindSharedDir(const MPD::SongList &);
|
||||||
#endif // HAVE_TAGLIB_H
|
#endif // HAVE_TAGLIB_H
|
||||||
std::string FindSharedDir(const std::string &, const std::string &);
|
std::string FindSharedDir(const std::string &, const std::string &);
|
||||||
|
std::string ExtractTopDirectory(const std::string &);
|
||||||
|
|
||||||
std::string GetLineValue(std::string &, char = '"', char = '"', bool = 0);
|
std::string GetLineValue(std::string &, char = '"', char = '"', bool = 0);
|
||||||
|
|
||||||
void RemoveTheWord(std::string &s);
|
|
||||||
std::string ExtractTopDirectory(const std::string &);
|
|
||||||
|
|
||||||
#ifdef _UTF8
|
#ifdef _UTF8
|
||||||
std::basic_string<my_char_t> Scroller(const std::string &str, size_t &pos, size_t width);
|
std::basic_string<my_char_t> Scroller(const std::string &str, size_t &pos, size_t width);
|
||||||
#endif // _UTF8
|
#endif // _UTF8
|
||||||
|
|||||||
@@ -323,20 +323,10 @@ void Playlist::EnableHighlighting()
|
|||||||
|
|
||||||
bool Playlist::Sorting(MPD::Song *a, MPD::Song *b)
|
bool Playlist::Sorting(MPD::Song *a, MPD::Song *b)
|
||||||
{
|
{
|
||||||
|
CaseInsensitiveStringComparison cmp;
|
||||||
for (size_t i = 0; i < SortOptions; ++i)
|
for (size_t i = 0; i < SortOptions; ++i)
|
||||||
{
|
if (int ret = cmp((a->*(*SortDialog)[i].second)(), (b->*(*SortDialog)[i].second)()))
|
||||||
std::string sa = (a->*(*SortDialog)[i].second)();
|
return ret < 0;
|
||||||
std::string sb = (b->*(*SortDialog)[i].second)();
|
|
||||||
ToLower(sa);
|
|
||||||
ToLower(sb);
|
|
||||||
if (Config.ignore_leading_the)
|
|
||||||
{
|
|
||||||
RemoveTheWord(sa);
|
|
||||||
RemoveTheWord(sb);
|
|
||||||
}
|
|
||||||
if (sa != sb)
|
|
||||||
return sa < sb;
|
|
||||||
}
|
|
||||||
return a->GetPosition() < b->GetPosition();
|
return a->GetPosition() < b->GetPosition();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user