我有一个用于编译scala项目的ant文件。我使用的是fsc,它的工作原理是避免2~3秒,我的核心2只需要加载编译器。
我的问题是:就我所知,ant fsc任务确实会招致同样的2~3秒的惩罚。这是相当恼人的,因为有fsc专门因为这个原因。这甚至更烦人,因为它实际上是启动时间,而不是处理时间,所以我必须等待3秒的fsc任务,即使没有什么需要重新编译。每一次,它都会变得更加严重。
我的研究似乎表明,大部分时间都花在阅读Scala-编译器. that上。实际上,scalac和fsc任务需要这样做是有道理的,因为它们直接运行编译器。此外,从ant任务的类路径中删除Scala-编译器. for,当然会导致任务由于缺少依赖关系而失败。
从逻辑上讲,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下,您可以在不碰到这堵墙的情况下走得很远,但在windows下,需要几十个文件才能阻止上述操作。添加一个选项,将文件指定为相对路径,而不是绝对路径,这会给人一些感觉,但并不多。根据依赖项在多个命令中分割文件并不是一个现实的选择,因为它是一个相当繁重的任务,需要在文件结构发生变化时进行更新。因此,对于小型项目来说,上面提到的大部分都会解决这个问题,但对于任何规模可观的项目都没有帮助.
发布于 2010-11-21 17:29:59
希望这能帮到你:
第一例(fsc蚂蚁任务)
启动ant时,您将加载一个全新的JVM,在其中加载scala-compiler.jar。jar的加载是因为行<taskdef resource="scala/tools/ant/antlib.xml" classpath="${scala-library.jar}:${scala-compiler.jar}" />,而不是因为classpath部件。
第二种情况(ant启动命令行)
正如您概述的那样,这仅限于文件很少的简单项目。最大命令行长度: windows -> 8191,linux/osx ->内核值(通常>100000),这里生成两个JVM (一个用于ant,另一个用于fsc)。也许它在您的测试中使用缓存更快。
拟议解决方案
在maven中,目标是scala:cc (连续编译),它将编译器保存在内存中,并不断扫描文件以进行修改。如果不想将构建器更改为maven,也许可以编写一个新的ant任务,它可以执行相同的任务(fscc:快速scala连续编译器)
https://stackoverflow.com/questions/4020940
复制相似问题