2010-11-10 7 views
1

Есть ли способ выполнять функции и переменные подъем между исходным кодом, присутствующим в разных файлах? То есть, что-то вродеПодъем между различными файлами

//Inside firstfile.js 
foo === "bar" //should return true 

и

//Inside secondfile.js 
function bar() { 
    this.foo = "bar"; 
} 

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

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

+0

Это, похоже, не имеет ничего общего с подъемом. –

+0

Почему вы так говорите? – Andrea

+0

@Tim Down Я думаю, что термин «подъем» относится к тому факту, что Javascript интерпретирует объявления функций перед другим кодом. – Pointy

ответ

3

Первоначально я думал, что это был более интересный вопрос, чем кажется на самом деле. Ответ на вопрос, который, как я думал, состоял в том, что каждый элемент <script> представляет собой отдельный Program, каждая отдельная программа анализируется и (критически) выполняется до того, как что-либо произойдет со следующей Программой, поэтому эффекты подъема можно увидеть только в одной программе ,

Например, в рамках одного сценария:

«функции»
<script type="text/javasscript"> 
    alert(typeof foo); 
    function foo() {} 
</script> 

... предупреждения, потому что объявление функции поднятым, но раскалывать две строки в отдельных <script> элементов изменяет это:

<script type="text/javasscript"> 
    alert(typeof foo); 
</script> 
<script type="text/javasscript"> 
    function foo() {} 
</script> 

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

+0

Да, это то, о чем я просил; в основном я просто хотел подтвердить. Просто потому, что мне любопытно: это конкретное поведение браузеров, или это в спецификации ECMA? – Andrea

+1

Поведение программ хорошо определено в спецификации ECMAScript. То, что я никогда не мог найти, - это указать, что каждый элемент '

1

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

window.foo = "bar"; 

в одном исходном файле позволит другой источник (загруженную впоследствии), чтобы проверить:

if (window.foo === "bar") { 
    // do something 
} 

Это должно работать, иначе это было бы невозможно создать что-то вроде все популярные Javascript рамки.

Ключевое слово «this» имеет смысл только внутри функции, и его значение не имеет ничего общего с исходным файлом, из которого была получена функция (по крайней мере, ни в каком прямом смысле).

редактировать — Я думаю, что самое интересное здесь поведение интерпретатора Javascript, что (чтобы использовать этот термин в вопросе) «распускает» объявление функций перед другим кодом в блоке оценивается. Это также выполняется по сценарию по сценарию, когда браузер загружает их. Таким образом, объявления функций в блоке сценария интерпретируются перед другим кодом в каждом блоке, но один тег <script> будет полностью оценен до того, как будет загружен и оценен следующий тег <script>.

Все становится более сложным, если вы используете что-то вроде LabJS или enhance.js для загрузки скриптов, но я не знаю ни одного контекста, в котором вы могли бы полагаться на скрипты «смешивание вместе» как-то если вы явно не объединить их на сервере.

+0

Конечно, отдельно загруженные источники Javascript могут влиять на глобальный контекст. Моя проблема заключается в том, может ли файл изменить глобальное пространство для файла, который был загружен ранее. – Andrea

+0

Что касается использования этого, то в этом контексте он ссылается на глобальный объект, поэтому this.foo - это просто foo. Если два фрагмента были в одном файле, в порядке, указанном в моем сообщении, сравнение вернет true, хотя значение «bar» назначается ПОСЛЕ сравнения. Моя проблема заключается в том, может ли этот механизм работать в разных файлах. – Andrea

+0

О, я понимаю, о чем вы говорите; Я уточню свой ответ. – Pointy

1

Все теги сценариев, которые встречаются в браузере, анализируются и выполняются немедленно. Это из-за документа.write API, который может потребовать, чтобы браузер выводил что-то в DOM. Это означает, что в этой ситуации # script1 должен заканчиваться до # script2.

<script id="script1"></script> 
<script id="script2"></script> 

Возможно, вы захотите проверить поведение при использовании атрибутов ASYNC и DEFER. Они поддерживаются в Webkit.

Смежные вопросы