У меня есть файл ant, который я использую для компиляции моего проекта scala. Я использую fsc, который творит чудеса, чтобы избежать 2 ~ 3 секунд, чтобы ядро 2 просто загрузило компилятор.
Моя проблема заключается в том, что задача ant fsc
выполняет те же штраф 2 ~ 3 секунды, насколько мне известно. Это довольно раздражает, потому что именно по этой причине есть fsc. Это еще более раздражает, так как это действительно время начала и не время обработки, поэтому я должен ждать 3 секунды в fsc-задаче, даже если перекомпилировать нечего. Каждый раз он становится обостряющимся.
Мои исследования показывают, что большинство времени тратится на чтение scala -compiler.jar. Действительно, имеет смысл выполнять задачи scalac
и fsc
, так как они запускают компилятор напрямую. Кроме того, удаление scala -compiler.jar из пути к классам результатов задачи ant, конечно же, приводит к сбою задачи из-за отсутствия зависимости.
Логически говоря, задача fsc
связана только с компиляцией dæmon, я полагаю, поэтому она не должна нуждаться в этой зависимости, но я предполагаю, что она реализована (задача fsc наследует от задачи scala). Возможно, это будет в следующей версии.
В настоящее время решение, которое я рассматриваю, переписывает мою задачу fsc как задачу приложения и вызывает fsc вручную. Тогда у меня не будет задержки. Очень жаль, что нужно вручную переделать работу, которую задачи, включенные в scala, были специально написаны для обработки.
Есть ли у кого-нибудь опыт в этой проблеме? Что-то не так в моем анализе? И можете ли вы предложить лучшее решение, чем тот, который я планирую реализовать?
Для справки, вот как выглядит моя задача (да, она компилирует проект android):
<target name="compile-scala" description="Compile scala files">
<taskdef resource="scala/tools/ant/antlib.xml" classpath="${scala-library.jar}:${scala-compiler.jar}" />
<mkdir dir="${out.classes.absolute.dir}" />
<fsc encoding="utf-8" deprecation="on" destdir="${out.classes.absolute.dir}">
<src>
<dirset dir="." includes="src"/>
<dirset dir="." includes="gen"/>
</src>
<classpath>
<pathelement location="${android.jar}" />
<fileset dir="${sdk.dir}/tools/lib" includes="*.jar" />
</classpath>
</fsc>
</target>
Изменить. Вот как выглядит задача с применением. Кажется, это работает. Это, однако, довольно неудовлетворительно, поэтому вопрос по-прежнему сохраняется.
<target name="fast-compile-scala"
description="Compile scala files without loading the compiler inside ant">
<mkdir dir="${out.classes.absolute.dir}" />
<apply executable="fsc" failonerror="true" parallel="true">
<arg value="-encoding" />
<arg value="utf-8" />
<arg value="-deprecation" />
<arg value="-dependencyfile" />
<arg value="${out.classes.absolute.dir}/${scala.deps}" />
<arg value="-g:vars" />
<arg value="-d" />
<arg value="${out.classes.absolute.dir}" />
<arg value="-make:transitivenocp" />
<arg value="-classpath" />
<arg value="${android.jar}:${out.classes.absolute.dir}" />
<!-- <arg value="-optimize" /> -->
<!-- <arg value="-verbose" /> -->
<!-- <arg value="-explaintypes" /> -->
<fileset dir="src" includes="**/*.scala" />
<fileset dir="src" includes="**/*.java" />
<fileset dir="gen" includes="**/*.java" />
</apply>
</target>
Изменить снова: Вышеупомянутые работы, но я считаю, что это имеет довольно серьезные ограничения. Когда число файлов увеличивается, указанная задача ограничена количеством аргументов и/или длиной командной строки. В Linux или Mac OS с хорошей оболочкой вы можете пойти довольно далеко, не нажимая эту стену, но под окнами требуется всего несколько десятков файлов, чтобы предотвратить работу выше. Добавление опции для указания файлов как относительных путей вместо абсолютного дает некоторое дыхание, но не так много. Разделение файлов по нескольким командам в зависимости от зависимостей не является реалистичным вариантом, поскольку это довольно тяжелая задача и нуждается в обновлении всякий раз, когда изменяется структура файла. Так что, хотя для небольших проектов вышеупомянутое в основном решит проблему, это не поможет ни одному проекту достойного размера...