Подтвердить что ты не робот

Почему моя функция JavaScript иногда "не определена"?

Я вызываю свою функцию JavaScript. Почему иногда я получаю ошибку "myFunction не определен", когда она определена?

Например. Иногда я получаю "copyArray не определен" даже в этом примере:

function copyArray( pa ) {
    var la = [];
    for (var i=0; i < pa.length; i++)
        la.push( pa[i] );
    return la;
}

Function.prototype.bind = function( po ) {
    var __method = this;
    var __args = [];

    // Sometimes errors -- in practice I inline the function as a workaround.
    __args = copyArray( arguments );

    return function() {
        /* bind logic omitted for brevity */
    }
}

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

Я получаю это в ситуациях, которые труднее работать, когда вызывающая функция находится в другом файле, который должен быть загружен после вызываемой функции. Но это был самый простой случай, который я мог представить, и, похоже, та же проблема.

Это не происходит в 100% случаев, поэтому я подозреваю, что проблема связана с нагрузкой. Но я понятия не имею, что.

@Hojou: Эта часть проблемы. Функция, в которой я сейчас получаю эту ошибку, сама по себе является моей addLoadEvent, которая в основном является стандартной версией общей библиотечной функции.

@James: Я так понимаю, и в функции нет синтаксической ошибки. В этом случае также сообщается о синтаксической ошибке. В этом случае я получаю только "неопределенную" ошибку.

@David: script в этом случае находится во внешнем файле, на который ссылаются, используя обычный < script src= "file.js" > </script> метод в разделе главы страницы.

@Douglas: Интересная идея, но если бы это было так, как мы могли бы с уверенностью назвать пользовательскую функцию? В любом случае я пробовал это, и он не работал.

@sk: эта методика была протестирована в браузерах и в основном скопирована из библиотеки Prototype.

4b9b3361

Ответ 1

Невозможно, чтобы это произошло, если вы просто включили скрипты на странице.

Функция copyArray всегда должна быть доступна, когда код JavaScript начинает выполняться независимо от того, объявлен ли он до или после него - если вы не загружаете файлы JavaScript динамически с помощью библиотеки зависимостей. В этом случае есть проблемы со сроками.

Ответ 2

У меня была эта функция, которая не распознавалась, как она определена в последнем Firefox для Linux, хотя Chromium отлично справлялся с ней.

В моем случае произошло то, что перед блоком, который определил функцию с проблемой, у меня был прежний блок SCRIPT, указанный следующим образом:

<SCRIPT src="mycode.js"/>

(То есть без закрывающего тега.)

Мне пришлось переделать этот блок следующим образом.

<SCRIPT src="mycode.js"></SCRIPT>

И потом, что после этого работало нормально... странно, да?

Ответ 3

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

Ответ 4

Подтвердите свой код с помощью JSLint. Обычно он найдет тонну небольших ошибок, поэтому предупреждение "JSLint может повредить вашим чувствам" довольно хорошо. =)

Ответ 5

Синтаксическая ошибка в функции - или в коде выше - может быть undefined.

Ответ 6

Если вы меняете прототип встроенного объекта "function", возможно, вы используете ошибку браузера или состояние гонки, изменяя фундаментальный встроенный объект.

Проверьте его в нескольких браузерах, чтобы узнать.

Ответ 7

Это не решит вашу оригинальную проблему, но вы всегда можете заменить вызов copyArray() на:

__args = Array.prototype.slice.call(arguments);

Дополнительная информация доступна из Google.

Я тестировал выше в следующих браузерах: IE6, 7 и 8B2, Firefox 2.0.0.17 и 3.0.3, Opera 9.52, Safari для Windows 3.1.2 и Google Chrome (какая бы ни была последняя версия в то время этого сообщения), и он работает во всех браузерах.

Ответ 8

Это, вероятно, было исправлено, но... очевидно, что firefox имеет проблему кэширования, которая является причиной того, что функции javascript не распознаются. Я действительно не знаю специфики, но если вы очистите свой кеш, который будет исправлять проблема (пока ваш кеш не будет снова заполнен... не очень хорошее решение). Я искал, чтобы посмотреть, есть ли у firefox реальное решение этого, но пока ничего... о не все версии, я думаю, это может быть только в некоторых версиях 3.6.x, не уверен...

Ответ 9

Используйте анонимную функцию для защиты вашей локальной таблицы символов. Что-то вроде:

(function() {
    function copyArray(pa) {
        // Details
    }

    Function.prototype.bind = function ( po ) {
        __args = copyArray( arguments );
    }
})();

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

Ответ 10

Я боюсь, что когда вы добавляете новый метод в класс Function (путем prtotyping), вы фактически добавляете его ко всем объявленным функциям AS WELL AS к вашему copyArray(). В результате ваша функция copyArray() получает рекурсивно саморегуляцию. То есть должен существовать метод copyArray(). bind(), который вызывает себя.

В этом случае некоторые браузеры могут помешать вам создать такие циклы ссылок и пожарную ошибку "функция не определена".

В этом случае встроенный код будет лучшим решением.

Ответ 11

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

Ответ 12

Я думаю, что ваш javascript-код должен быть помещен между тегом, требуется загрузка документа

Ответ 13

Решено, удалив "асинхронную" нагрузку:

  <script type="text/javascript" src="{% static 'js/my_js_file.js' %}" async></script>

изменено для:

  <script type="text/javascript" src="{% static 'js/my_js_file.js' %}"></script>

Ответ 14

Убедитесь, что ваша функция не является непреднамеренно вложенной функцией, скажем, что она была определена в функции, которая обрабатывает событие готовности документа.