Селектор jQuery: почему $ ("# id"). find ("p") быстрее чем $ ("# id p") - PullRequest
7 голосов
/ 19 января 2012

Автор этой страницы: http://24ways.org/2011/your-jquery-now-with-less-suck утверждает, что селектор jQuery $('#id').find('p') быстрее, чем $('#id p'), хотя это, вероятно, дает те же результаты, если я правильно понимаю. В чем причина такой разницы?

Ответы [ 2 ]

6 голосов
/ 19 января 2012

Потому что $('#id').find('p') оптимизирован для выполнения ...

document.getElementById('id').getElementsByTagName('p');

... тогда как я предполагаю, что $('#id p') будет использовать querySelectorAll, если доступно, или механизм выбора на основе JavaScript, если нет.


Вы должны отметить, что производительность всегда имеет различия между браузерами. Опера, как известно, имеет чрезвычайно быстрый querySelectorAll.

Кроме того, разные версии jQuery могут предлагать разные оптимизации.

Возможно, $('#id p') будет (или в настоящее время) при той же оптимизации, что и первая версия.

2 голосов
/ 19 января 2012

Это зависит от браузера, так как jQuery использует querySelectorAll, когда он доступен.Когда я тестировал в WebKit, это было действительно быстрее.Как выясняется, querySelectorAll оптимизировано для этого случая.

Внутри WebKit, если весь селектор равен #<id> и в документе есть только один элемент с таким идентификатором, он оптимизируется до getElementById.Но, если селектор - что-то еще, querySelectorAll пересекает документ, ища элементы, которые соответствуют.

Да, должна быть возможность оптимизировать этот случай так, чтобы они выполняли то же самое - но сейчас, никтоесть.Вы можете найти его здесь в источнике WebKit, SelectorDataList::execute использует SelectorDataList::canUseIdLookup, чтобы решить, использовать ли getElementById.Выглядит это так:

if (m_selectors.size() != 1)
    return false;
if (m_selectors[0].selector->m_match != CSSSelector::Id)
    return false;
if (!rootNode->inDocument())
    return false;
if (rootNode->document()->inQuirksMode())
    return false;
if (rootNode->document()->containsMultipleElementsWithId(m_selectors[0].selector->value()))
    return false;
return true;

Если вы тестировали в браузере, отличном от WebKit, возможно, в нем отсутствуют подобные оптимизации.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...