Pull to refresh
0
0

User

Send message
Ну а я-то проверял в предыдущих версиях. А Вы какой дебаггер на FF3 установили?
>у меня получилось примерно следующее

Это в Firefox'е? А какая версия?
>ммм, я уже высказал предположение...

Вы мне ответьте - в вашем Firefox'е после трех сгенерированных кликов все интервальные функции выполняются сразу?

>Я даже не предполагал, что на них (различия в правилах) стоит как-то закладываться при создании приложений

А как на это не обращать внимание, если в IE, например, метод setInterval работает, как часы (т.е. интервал между вызовами функций всегда тот, который был задан), а в Firefox'е функции могут быть вызваны целым "скопом" (т.е. без интервала), если до этого скриптовый движок был "сильно" занят?
>что показывает данная функция

Я ведь предлагал с самого начала посмотреть на результаты выполнения в Firefox. Смотрели? Заметили, что в отличие, например, от IE после выполнения трех обработчиков события click (на которые ушло времени столько, сколько нужно было на выполнение всех интервальных функций), все интервальные функции выполняются практически сразу?

>Вы ведь потратили время, чтобы ее написать.

Написано давно для форумных дискуссий. Т.ч. не печальтесь по поводу истраченного времени - у меня таких тестовых примеров еще много (и по этой теме еще есть, опять же подтверждающее то, что автор статьи не имеет представления о том, что написал). ;)
А к чему вторая дискуссия? Я выводы по поводу статьи уже сделал ранее. А эту функцию выложил, т.к. первый раз с ошибками опубликовал ее урезанный вариант.
Вот функция, которая позволит проследить за различием в выполнении метода setInterval в браузерах IE, Opera, FF, Safari и проч.
При событии onload документа эта функция генерирует 3 (по умолчанию) клика на документе. Самому кликать не нужно, иначе в результатах будет сложнее разрираться. Первый из обработчиков клика запускает интервальную функцию.


window.onload = function () {
var numberOfCalls = 0;
/* numberOfCalls - numeration of function' calls (so no one won't be lost)
!!! it should be equaled always to zero
*/
var callsLimit = 5; // the limit of function calls
var interval = 1000; // desirable interval between calls (not reliable)
var execTime = 2000; // time of execution of every onclick handler
var numberOfClicks = 3; // number of simulated clicks on document
var startDate = new Date;
var reg = /function|object/;
var debugLog = function (aReg) {
var fnBody;
if (aReg.test(typeof (Debug)) &&
aReg.test(typeof (Debug.write))) {
fnBody = 'Debug.write(aMsg);'; // IE
} else if (aReg.test(typeof (opera)) &&
aReg.test(typeof (opera.postError))) {
fnBody = 'opera.postError(aMsg);'; // Opera
} else if (aReg.test(typeof (console)) &&
aReg.test(typeof (console.log))) {
fnBody = 'console.log(aMsg);'; // FF, Safari etc.
} else {
return new Function;
};
return new Function('aMsg', fnBody);
}(reg);
var onClickListener = function () {
var s = new Date;
while ((new Date) - s < execTime);
debugLog('onclick handler: '
.concat((new Date) - startDate,
'ms since document has loaded.'));
if (numberOfCalls == 0) {
numberOfCalls++;
debugLog('setting interval');
var id = setInterval(function () {
if (numberOfCalls > callsLimit) {
return clearInterval(id);
};
debugLog('interval call number '
.concat(numberOfCalls++,
': ', (new Date) - startDate,
'ms since document has loaded.',
' (expected: ',
interval * (numberOfCalls - 1),
'ms).'));
}, interval);
};
};
(function (aEvt, aDoc, aClicks, aReg) {
var func;
if (!aReg.test(typeof (setInterval))) {
return false;
};
if (aReg.test(typeof (aDoc.addEventListener)) &&
aReg.test(typeof (aDoc.createEvent)) &&
aReg.test(typeof (aDoc.dispatchEvent))) {
var evt = aDoc.createEvent('MouseEvents');
if (aReg.test(evt.initMouseEvent)) {
func = function () {
evt.initMouseEvent(aEvt, true, true, window,
0, 0, 0, 0, 0, false, false,
false, false, 0, null);
aDoc.dispatchEvent(evt);
};
aDoc.addEventListener(aEvt, onClickListener, false);
};
} else if (aReg.test(typeof (aDoc.attachEvent)) &&
aReg.test(typeof (aDoc.fireEvent))) {
func = function () {
aDoc.fireEvent(aEvt);
};
aDoc.attachEvent(aEvt = 'on' + aEvt, onClickListener);
};
if (func) {
debugLog('The script has started, '
.concat(aClicks,
' clicks on the document is expected.',
' (each of them should take ',
execTime, 'ms).'));
while (aClicks-- > 0) {
func();
};
};
}('click', document, numberOfClicks, reg));
};

Искренне извиняюсь, что заставил Вас разбираться с моей ошибкой. А ошибку допустил при копировании, пропустив икремент переменной i, который должен находиться в первой строке блока условия if (i == 0).
Примите извинения.
Сейчас, начав новую ветвь (т.к. здесь уже места нет для кода), опубликую тестовую функцию, которая наглядно покажет отличия в разных браузерах (IE, Opera, FF, Safari).
>если у нас кликов меньше 7, то Ваше заявление неверное.

Повторяю еще раз - метод setInterval вызывается лишь один раз (всегда и везде!!!). Это происходит в момент первого клика по документу. Во всех остальных кликах условие: if (i == 0) просто невыполняется.

>не демонстрирует заявленную в статье функциональность

Я уже написал то, что думаю об этой статье. Принимать мое мнение во внимание или нет - ваше личное дело.
>ну, в общем случае, не каждый.

Да не "в общем случае", а так и есть. Иначе резульаты теста были вообще непонятны.

>Но это слабо меняет картину :)

Картина такая. Описываемое в статье - это одно из двух:
1. или относящееся лишь к поведению одной реализации (а их ведь больше, чем одна);
2. или вообще не соответствующее действительности.
>Так Ваши слова понимать?

Вы написали: "У Вас каждый onclick выставляет после своего выполнения setInterval'ом анонимную функцию...". А я Вам ответил, что это не так (обратите внимание на то, что я выделил). ;)
>У Вас каждый onclick выставляет после своего выполнения setInterval'ом анонимную функцию

Ничего подобного! :) Будьте внимательней! :)

>Должно ли "сброситься" ее выполнение и в каких браузерах?

Не должно...

>у меня после полутора десятков кликов выполнились все 6 интервалов даже в Firefox

Естественно. Другое дело - как они выполняются в разных браузерах. А выполняются они по-разному: например, как Вы могли заметить, в Firefox'е они выполняются сразу. А вот, к примеру, в IE совершенно противоположная картина. И т.д...
>Таймеры в разных браузерах работают по разному?

Да, конечно. Чуть ниже в комментах я опубликовал небольшой кусочек кода. Прочтите этот коммент.

>попробуйте генерить JS-ом таблицу хотя бы 10 колонок...

Хотелось бы увидеть пример, а не самому его писать (я, как правило, так и делаю, если нужно что-то объяснить). Ну да ладно - на нет и суда нет...
Вот небольшой пример, который нужно выполнить в Firefox'е. Поместите его в какой-нибудь документ и кликните раза три. Затем попытайтесь объяснить результат, появившийся в консоли:


(function () {
var i = 0, d = new Date;
document.onclick = function () {
var s = new Date;
while ((new Date) - s < 2000);
console.log((new Date) - d);
if (i == 0) {
var id = setInterval(function () {
if (i > 5) {
return clearInterval(id);
};
console.log(i++ + ': ' + ((new Date) - d));
}, 1000);
};
};
}());

>в данном контексте не выставляется в очередь на выполнение

var id = window.setInterval(myFunc, 100);
Выставлено на выполнение каждые 100мс, так? Однако, выполнение может быть отложено. В каком же контексте понимать "не выставляется в очередь"?

>но продолжает проверяться

Что продолжает проверяться?
>Один на документ/страницу/закладку

Проверьте свое предположение, например, в Firefox.
>1. да

Нет!

>движок однако "ставит на паузу" выполнение кода…

Как это можно проверить?
>1. да

Нет!!!
>Просто чуть-чуть увеличиваем производительность…

"Увеличиваем производительность" за счет установки дополнительных таймеров, а также возможного сброса и повторной установки интервала?
>Таймерное событие, в случае _действительно_ длинной очереди, всё равно обязано выполнится раньше, потеснив другое событие.

"Потеснив другое событие" – интересная теория. :) А что на практике?
>Однако, стоит обратить внимание, Что при последующем срабатывании того же таймера (interval), он сбрасывается.

Что значит "он сбрасывается"?

Information

Rating
Does not participate
Registered