JavaScript: document.getElementById замедляют производительность?

Мы должны связываться с фактическими источниками информации, а не просто главным хитом Google.

http://developer.mozilla.org/En/Core_JavaScript_1.5_Reference/Reserved_Words

JScript 8.0: http://msdn.microsoft.com/en-us/library/ttyab5c8.aspx

15
задан TeddyH 11 November 2009 в 16:17
поделиться

9 ответов

Для меня это было бы более подходящим и хорошим для производительности:

var desc = document.getElementById("desc");
var asc = document.getElementById("asc");
desc.setAttribute("href","#");
asc.onclick = function() { ... }
...

После пересмотра того, что сказал ChaosPandion, я думаю один из способов сделать это:

var elements = ["desc", "asc", ...];
for(var i = 0; i < elements.length; i++) {
  GlobalElementId[elements[i]] = document.getElementById(elements[i]);
}
3
ответ дан 1 December 2019 в 01:23
поделиться

Поскольку вы говорите «CSS-элементы», я подозреваю, что большая часть вашей низкой производительности не из-за повторяющегося использования document.getElementById () (которого вам в любом случае следует избегать ), а сколько раз вы изменяли объект стиля для данного узла.

Каждый раз, когда вы меняете свойство в стиле , вы заставляете браузер повторно рисовать этот элемент и, возможно, многие другие на странице.

var elem = document.getElementById( 'desc' );
elem.style.textDecoration = "none"; // browser re-draw
elem.style.borderWidth    = "2px";  // browser re-draw
elem.style.paddingBottom  = "5px";  // browser re-draw

Здесь лучшим решением является использование классов CSS и переключение или добавление / удаление имени класса из узла. Это позволяет вам упаковать столько изменений стиля, сколько вы хотите, за счет всего лишь одной перерисовки.

var elem = document.getElementById( 'desc' );
elem.className = "whatever"; // Only one browser re-draw!
7
ответ дан 1 December 2019 в 01:23
поделиться

Да!

Недавно была ситуация, когда я получал изменяющие элементы с низкой производительностью. Решением было создать словарь, подобный вашему примеру. Я буквально в 1000 раз улучшил производительность (по крайней мере, в IE6).

var elementCache = {};
function buildElementCache() {
    elementCache[id] = {
        element1: document.getElementById(id + "1"),
        element2: document.getElementById(id + "2")
    } 
    // Etc...   
}
2
ответ дан 1 December 2019 в 01:23
поделиться

Итак, все «да» ответы меня раздражали, поэтому я на самом деле рассчитал время, чтобы увидеть, работает ли getElementById медленно!

Вот результаты ( для страницы с 10 000 элементов на ней ):

IE8 getElementById: 0,4844 мс
Поиск в массиве идентификаторов IE8: 0,0062 мс

Chrome getElementById: 0,0039 мс
Поиск в массиве идентификаторов Chrome: 0,0006 мс

Firefox 3.5 был сопоставим с Chrome.

Полмиллисекунды на вызов функции не заставят меня использовать массив;) Но может быть хуже на IE6, который у меня не установлен.

Вот мой сценарий:

<html>
<head>
<script type="text/javascript">
    var numEles = 10000;
    var idx = {};

    function test(){
        generateElements();
        var t0 = (new Date()).getTime();
        var x = selectElementsById();
        var t1 = (new Date()).getTime();
        var time = t1 - t0;
        generateIndex();
        var t2 = (new Date()).getTime();
        var x = selectElementsWithIndex();
        var t3 = (new Date()).getTime();
        var idxTime = t3 - t2;

        var msg = "getElementById time = " + (time / numEles) + " ms (for one call)\n"
            + "Index Time = " + (idxTime/ numEles) + " ms (for one call)";
        alert(msg);
    }

    function generateElements(){
        var d = document.getElementById("mainDiv");
        var str = [];
       for(var i=0;i<numEles;i++){
           str.push("<div id='d_" + i + "' >" + i + "</div>");
        }
        d.innerHTML = str.join('');
    }

    function selectElementsById(){
        var eles = [];
        for(var i=0;i<numEles;i++){
            var id = ((i * 99) % numEles);
            eles.push(document.getElementById("d_" + id));
        }
        return eles;
    }

    function generateIndex(){
        for(var i=0;i<numEles;i++){
            var id = "d_" + i;
           idx[id] = document.getElementById(id);
        }
    }

    function selectElementsWithIndex(){
        var eles = [];
        for(var i=0;i<numEles;i++){
            var id = ((i * 99) % numEles);
            eles.push(idx["d_" + id]);
        }
        return eles;
    }   
</script>
</head>
<body onload="javascript:test();" >
<div id="mainDiv" />
</body>
</html>
22
ответ дан 1 December 2019 в 01:23
поделиться

Зависит от определения термина «значительный». Доступ к массиву GlobalElementId.asc происходит намного быстрее пропорционально, чем вызов getElementById () . Но getElementById по-прежнему очень быстр по сравнению с большинством других манипуляций с DOM, которые ваш скрипт, вероятно, будет делать, и, по всей вероятности, составляет лишь очень-очень маленькую часть времени выполнения вашего скрипта.

Я бы написал во-первых, для удобочитаемости, для чего ответ Суфиан кажется лучшим. Только если бы на практике эта часть скрипта оказалась слишком медленной, я бы стал думать о кэшах поиска, которые добавляют дополнительную сложность (особенно если вы начинаете изменять эти элементы во время выполнения).

Примечание: не используйте setAttribute , это '

1
ответ дан 1 December 2019 в 01:23
поделиться

Короткий ответ - да, в любое время вы можете сделать переменная Javascript или локальная ссылка на объект, это поможет с производительностью.

Если вам нужно более глубокое понимание управления областью видимости и его последствий для производительности Javascript, в техническом разговоре Speed ​​Up Your Javascript есть некоторые действительно хорошая информация. Настоятельно рекомендуется просмотр.

1
ответ дан 1 December 2019 в 01:23
поделиться

Да, но использование массива - это перебор.

См. ответ Суфиане Хассу, чтобы узнать, как это сделать.

0
ответ дан 1 December 2019 в 01:23
поделиться

Это называется кэшированием объектов, и это повысит производительность вашего скрипта.
См. Подробности на http://www.javascriptkit.com/javatutors/efficientjs.shtml .
Кроме того, если вы часто меняете CSS, я бы предложил использовать jQuery, как предлагает @Fahad.

0
ответ дан 1 December 2019 в 01:23
поделиться

Нет, значительного прироста производительности не будет. Ваши проблемы с производительностью кроются в другом месте. В браузере есть собственный индекс для элемента id -> element object.

Если вы хотите выяснить, почему ваш код медленный, очень важно рассчитать время, потому что медленная часть, вероятно, не то, что вы ожидали (I нашел это на собственном горьком опыте). Вы можете сделать это следующим образом:

var t0 = (new Date()).getTime();
var t1 = (new Date()).getTime();
var time = t1 - t0;

Хотя важно отметить, что здесь точность составляет 15 мс, что означает, что если что-то занимает 14 мс, в некоторых браузерах оно может отображаться как 0 мс.

Вот как ваш код будет выглядеть в jQuery:

$("#desc").attr("href", "#")
    .click(function(){})
    .css("text-decoration", "none");
0
ответ дан 1 December 2019 в 01:23
поделиться
Другие вопросы по тегам:

Похожие вопросы: