Может ли минификатор сделать это? (и это хорошая идея?)

У меня есть приложение JavaScript, которое генерирует значительное количество элементов DOM. Это означает, что я часто использую document.createElement("tagname") в своем сценарии.

Я думаю об использовании этой простой функции:

function c(e) {return document.createElement(e);}

Я бы продолжал писать свой код на JavaScript (или, может быть, на CoffeScript) и использовал в коде полный метод document.createElement для удобочитаемости. Но я ожидаю, что когда я «компилирую» или минимизирую код, все экземпляры document.createElement заменяются функцией c.

Я бы сделал то же самое для других методов: document.getElementById и т. д. Я надеюсь, что с помощью этой техники смогу сократить свой код на 10–20%.

Существуют ли минификаторы или компиляторы, которые могут это сделать? И есть ли смысл изначально?


person Christophe    schedule 29.11.2011    source источник
comment
На какие преимущества вы рассчитываете?   -  person Ash Burlaczenko    schedule 30.11.2011
comment
Если ничего другого, вы всегда можете сделать это самостоятельно в качестве шага предварительной минификации. Не должно быть слишком сложно написать сценарий.   -  person cdeszaq    schedule 30.11.2011
comment
Вы сжимаете файлы? Держу пари, что это не будет иметь большого значения в долгосрочной перспективе.   -  person RightSaidFred    schedule 30.11.2011
comment
Почему бы просто не использовать c = document.createElement? EDIT: Нет, это ошибки. createElement должен вызываться из объекта документа. Самое близкое, что вы можете получить, это c = document.createElement.bind(document)   -  person Eric    schedule 30.11.2011
comment
@Ash: преимущество заключается в меньшем размере js-файла (выигрыш от 10 до 20%, как я сказал в вопросе).   -  person Christophe    schedule 30.11.2011
comment
Создавать слишком много элементов DOM? Начните использовать шаблоны JavaScript: ejohn.org/blog/javascript-micro-templating   -  person peterp    schedule 30.11.2011
comment
Обычно вы все равно сжимаете свой код. Минификация ИМХО предназначена для проектов, где важен каждый байт.   -  person tereško    schedule 30.11.2011


Ответы (5)


Я не думаю, что это принесет вам столько. Несжатый файл js может быть немного меньше, но сжатие должно иметь дело с такой повторяющейся строкой. Поэтому я ожидаю, что выигрыш от сжатого (сжатие http gzip) файла javascript будет довольно небольшим.

person CodesInChaos    schedule 29.11.2011
comment
Я считаю, что размер gzip-функции псевдонима на самом деле будет больше, поскольку сами функции псевдонима учитываются в дополнительных байтах... - person Stephen Chung; 01.12.2011

Я просто вызываю функцию create(e) вместо c(e). Таким образом, вы получаете лучшее из обоих миров, удобочитаемость и вам не нужно печатать так много.

person Bjørn Kjos-Hanssen    schedule 29.11.2011

Большинство минификаторов не будут переопределять библиотечные функции DOM с более короткими версиями. Однако во многих библиотеках вы видите этот шаблон, созданный вручную для сокращения и/или упрощения кода. Так что нет ничего плохого в том, чтобы сделать это самостоятельно. Просто убедитесь, что вы делаете это внутри замыкания....

Взгляните на параметры uglifier и посмотрите, что он может сделать для вас, например:

{
  :mangle => true, # Mangle variables names
  :toplevel => false, # Mangle top-level variable names
  :except => [], # Variable names to be excluded from mangling
  :max_line_length => 32 * 1024, # Maximum line length
  :squeeze => true, # Squeeze code resulting in smaller, but less-readable code
  :seqs => true, # Reduce consecutive statements in blocks into single statement
  :dead_code => true, # Remove dead code (e.g. after return)
  :lift_vars => false, # Lift all var declarations at the start of the scope
  :unsafe => false, # Optimizations known to be unsafe in some situations
  :copyright => true, # Show copyright message
  :ascii_only => false, # Encode non-ASCII characters as Unicode code points
  :inline_script => false, # Escape </script
  :quote_keys => false, # Quote keys in object literals
  :beautify => false, # Ouput indented code
  :beautify_options => {
    :indent_level => 4,
    :indent_start => 0,
    :space_colon => false
  }
}
person maxl0rd    schedule 29.11.2011

Это имеет смысл, но минификатор, который делает это автоматически, должен быть умным в нескольких вещах:

  1. Достаточно ли раз повторяется часть кода, преобразованная в новую функцию, чтобы сделать этот рефакторинг более экономичным?
  2. Потенциальное снижение производительности из-за упаковки кода в дополнительные функции: особенно когда этот код используется очень часто в критическом по времени сценарии (профилировщик может это определить, минификатор, вероятно, не может). Возможно, минификатор может ограничить количество замен в глубоко вложенных вызовах функций и т. д.

Вероятно, вам лучше сделать это вручную.

person Ates Goral    schedule 29.11.2011
comment
Будет ли снижение производительности, если я просто сделаю переименование, как предлагает Эрик: c=document.createElement ? - person Christophe; 30.11.2011

Это полностью зависит от минификатора. Большинство этого не делает. Например, код:

window['a'] = document.createElement('div');
window['b'] = document.createElement('div');
window['c'] = document.createElement('div');

В расширенном режиме Google Closure Compiler:

window.a=document.createElement("div");window.b=document.createElement("div");window.c=document.createElement("div");

На YUI-компрессоре:

window.a=document.createElement("div");window.b=document.createElement("div");window.c=document.createElement("div");

На jscompress.com:

window["a"]=document.createElement("div");window["b"]=document.createElement("div");window["c"]=document.createElement("div")

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

person Simon Sarris    schedule 29.11.2011