summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorIulian Dragos <jaguarul@gmail.com>2004-10-21 09:50:39 +0000
committerIulian Dragos <jaguarul@gmail.com>2004-10-21 09:50:39 +0000
commitbb73b041480e06dac7fc1e851776a3654541e594 (patch)
treef78fcf08525241a104caf364f4aec43b54f3ed75
parentd67d3c2ebad1a373c6e8abb7603394f8d7444e1a (diff)
downloadscala-bb73b041480e06dac7fc1e851776a3654541e594.tar.gz
scala-bb73b041480e06dac7fc1e851776a3654541e594.tar.bz2
scala-bb73b041480e06dac7fc1e851776a3654541e594.zip
Scala benchmark suite added
-rw-r--r--config/list/library.lst1
-rw-r--r--sources/scala/testing/Benchmark.scala74
-rw-r--r--test/benchmark/build.xml22
-rw-r--r--test/benchmark/predef.xml78
4 files changed, 175 insertions, 0 deletions
diff --git a/config/list/library.lst b/config/list/library.lst
index 43cd4e6807..544c29cde6 100644
--- a/config/list/library.lst
+++ b/config/list/library.lst
@@ -184,6 +184,7 @@ runtime/types/JavaTypeRepository.java
testing/UnitTest.scala
testing/SUnit.scala
+testing/Benchmark.scala
util/alphabet/Alphabet.scala
util/alphabet/AlphabetPlusWildcard.scala
diff --git a/sources/scala/testing/Benchmark.scala b/sources/scala/testing/Benchmark.scala
new file mode 100644
index 0000000000..f6523a7271
--- /dev/null
+++ b/sources/scala/testing/Benchmark.scala
@@ -0,0 +1,74 @@
+/* __ *\
+** ________ ___ / / ___ Scala API **
+** / __/ __// _ | / / / _ | (c) 2003-2004, LAMP/EPFL **
+** __\ \/ /__/ __ |/ /__/ __ | **
+** /____/\___/_/ |_/____/_/ | | **
+** |/ **
+** $Id$
+\* */
+
+
+/**
+ * Scala benchmarking mini framework.
+ */
+
+package scala.testing;
+
+/** <code>Benchmark</code> can be used to quickly turn an existing
+ * class into a benchmark. Here is a short example:
+ *
+ * <pre>
+ * object sort1 extends Sorter with Benchmark {
+ * def run = sort(List.range(1, 1000));
+ * }
+ * </pre>
+ *
+ * The run method has to be defined by the user, who will perform
+ * the timed operation there.
+ * Run the benchmark as follows:
+ * <pre>
+ * scala sort1 5 times.log
+ * </pre>
+ * This will run the benchmark 5 times and log the execution times in
+ * a file called times.log
+ */
+trait Benchmark {
+
+ /** this method should be implemented by the concrete benchmark */
+ def run: Unit;
+
+ /** Run the benchmark the specified number of times
+ * and return a list with the execution times in milliseconds
+ * in reverse order of the execution */
+ def runBenchmark(noTimes: Int): List[Long] =
+
+ for (val i <- List.range(1, noTimes + 1)) yield {
+ val startTime = System.currentTimeMillis();
+ run;
+ val stopTime = System.currentTimeMillis();
+ System.gc();
+
+ stopTime - startTime
+ }
+
+ /**
+ * The entry point. It takes two arguments: the number of
+ * consecutive runs, and the name of a log file where to
+ * append the times.
+ *
+ */
+ def main(args: Array[String]): Unit = {
+ if (args.length > 1) {
+ val logFile = new java.io.FileWriter(args(1), true); // append, not overwrite
+
+ logFile.write(getClass().getName());
+ for (val t <- runBenchmark(Integer.parseInt(args(0))))
+ logFile.write("\t\t" + t);
+
+ logFile.write("\n");
+ logFile.flush();
+ } else
+ Console.println("Usage: scala benchmarks.program <runs> <logfile>");
+ }
+}
+
diff --git a/test/benchmark/build.xml b/test/benchmark/build.xml
new file mode 100644
index 0000000000..da7645d81e
--- /dev/null
+++ b/test/benchmark/build.xml
@@ -0,0 +1,22 @@
+<project name="benchmark" default="run.benchmark">
+
+ <import file="predef.xml"/>
+
+ <target name="init" depends="clean.benchmark">
+ <mkdir dir="${benchmark.classes.dir}"/>
+ </target>
+
+ <target name="clean.benchmark"
+ description="Clean the files generated for the benchmark classes">
+ <delete dir="${benchmark.classes.dir}"/>
+ </target>
+
+ <target name="run.benchmark"
+ description="Run the benchmark suite">
+
+ <subant inheritAll="false">
+ <fileset dir="${benchmark.sources.dir}" includes="*/build.xml"/>
+ </subant>
+ </target>
+
+</project>
diff --git a/test/benchmark/predef.xml b/test/benchmark/predef.xml
new file mode 100644
index 0000000000..72bab526fe
--- /dev/null
+++ b/test/benchmark/predef.xml
@@ -0,0 +1,78 @@
+<project name="predef">
+
+ <!-- Redefine accordingly to where you checked out your scala files -->
+ <!-- scala.home should point to the directory that contains the -->
+ <!-- "benchmark" directory -->
+ <property name="scala.home" value="${user.home}/scala"/>
+
+ <!-- Define some basic paths -->
+ <property name="benchmark.home" value="${scala.home}/test/benchmark"/>
+ <property name="benchmark.sources.dir"
+ value="${benchmark.home}/sources"/>
+ <property name="benchmark.classes.dir"
+ value="${benchmark.home}/classes"/>
+ <property name="log.file"
+ value="${benchmark.home}/times/times.log"/>
+
+ <!-- Define the scalac task -->
+ <taskdef name="scalac"
+ classname="scala.tools.scala4ant.ScalacTask$class"/>
+
+ <!-- Define a <run-benchmark> element that can be used to run -->
+ <!-- benchmarks -->
+ <!-- It accepts these attributes: -->
+ <!-- count - how many times to run each benchmark (default:3) -->
+ <!-- classname - the name of the class to be ran (default: -->
+ <!-- the name of the ant project -->
+ <!-- logfile - the location of the file where running times -->
+ <!-- are logged (default: ${log.file} property) -->
+ <!-- location - the location of the classfiles: it will end -->
+ <!-- up as head of the current classpath (default: -->
+ <!-- benchmark classes dir/project name -->
+ <macrodef name="run-benchmark">
+ <attribute name="count" default="3"/>
+ <attribute name="classname" default="benchmarks.${ant.project.name}"/>
+ <attribute name="logfile" default="${log.file}"/>
+ <attribute name="location" default="${benchmark.classes.dir}/${ant.project.name}"/>
+
+ <sequential>
+ <echo>** Running benchmark @{classname} in @{location}..</echo>
+ <exec executable="scala" failonerror="true">
+ <arg line="-cp @{location}:${java.class.path}"/>
+ <arg line="@{classname} @{count} @{logfile}"/>
+ </exec>
+ <echo>Done</echo>
+ </sequential>
+ </macrodef>
+
+ <!-- Define a <compile-benchmark> element that can be used to -->
+ <!-- compile benchmarks -->
+ <!-- It accepts these attributes: -->
+ <!-- compiler - the name of the scalac compiler to use. It is -->
+ <!-- useful in case you have multiple compilers -->
+ <!-- installed (default: scalac) -->
+ <!-- additionalArgs - additional arguments to pass to scalac -->
+ <!-- (default: none) -->
+ <!-- destination - the location where class files should be -->
+ <!-- created (default: benchmark classes dir/project -->
+ <!-- name) -->
+ <!-- files - the source files to be compiled -->
+ <macrodef name="compile-benchmark">
+ <attribute name="compiler" default="myscalac"/>
+ <attribute name="additionalArgs" default=""/>
+ <attribute name="destination" default="${benchmark.classes.dir}/${ant.project.name}"/>
+ <attribute name="files"/>
+
+ <sequential>
+ <echo>
+** Building project ${ant.project.name} to @{destination}</echo>
+
+ <exec executable="@{compiler}" failonerror="true">
+ <arg line="-d @{destination}"/>
+ <arg line="@{additionalArgs}"/>
+ <arg line="@{files}"/>
+ </exec>
+ </sequential>
+ </macrodef>
+
+</project> \ No newline at end of file