Skip to content

Commit 2a4935c

Browse files
glebmxzyfer
authored andcommitted
Clean up Compound_Selector::operator==
Implements equality for `Compound_Selector` in a cleaner and more efficient manner. Similar change for `Selector_List`: #2739 This does not fix the stack overflow reported in #2667, though it does change its location (because we no longer clone any nodes in `operator==`).
1 parent c04f5d7 commit 2a4935c

File tree

1 file changed

+10
-27
lines changed

1 file changed

+10
-27
lines changed

src/ast.cpp

Lines changed: 10 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -1012,34 +1012,17 @@ namespace Sass {
10121012

10131013
bool Compound_Selector::operator== (const Compound_Selector& rhs) const
10141014
{
1015-
// for array access
1016-
size_t i = 0, n = 0;
1017-
size_t iL = length();
1018-
size_t nL = rhs.length();
1019-
// create temporary vectors and sort them
1020-
std::vector<Simple_Selector_Obj> l_lst = this->elements();
1021-
std::vector<Simple_Selector_Obj> r_lst = rhs.elements();
1022-
std::sort(l_lst.begin(), l_lst.end(), OrderNodes());
1023-
std::sort(r_lst.begin(), r_lst.end(), OrderNodes());
1024-
// process loop
1025-
while (true)
1026-
{
1027-
// first check for valid index
1028-
if (i == iL) return iL == nL;
1029-
else if (n == nL) return iL == nL;
1030-
// the access the vector items
1031-
Simple_Selector_Obj l = l_lst[i];
1032-
Simple_Selector_Obj r = r_lst[n];
1033-
// skip nulls
1034-
if (!l) ++i;
1035-
if (!r) ++n;
1036-
// do the check now
1037-
else if (*l != *r)
1038-
{ return false; }
1039-
// advance now
1040-
++i; ++n;
1015+
if (&rhs == this) return true;
1016+
if (rhs.length() != length()) return false;
1017+
std::unordered_set<const Simple_Selector *, HashPtr, ComparePtrs> lhs_set;
1018+
lhs_set.reserve(length());
1019+
for (const Simple_Selector_Obj &element : elements()) {
1020+
lhs_set.insert(element.ptr());
10411021
}
1042-
// there is no break?!
1022+
for (const Simple_Selector_Obj &element : rhs.elements()) {
1023+
if (lhs_set.find(element.ptr()) == lhs_set.end()) return false;
1024+
}
1025+
return true;
10431026
}
10441027

10451028
bool Complex_Selector::is_superselector_of(Compound_Selector_Ptr_Const rhs, std::string wrapping) const

0 commit comments

Comments
 (0)