This repository was created during the course Computer Systems Performance
at the IT University of Copenhagen - by Andreas Trøstrup, Frederik Petersen, and Lucas Hanson.
It was created to compare the energy consumption of different programming languages, specifically C, Java, JavaScript, TypeScript, Ruby, and Zig.
The paper concluded that even though there is a tendency for compiled languages to use less energy it is hard to draw strict conclusions from the data. This is due to that implmentation, the transpiler chosen, the libraries used, and the hardware used all have a significant impact on the energy consumption of the program.
This program was run on a Raspberry Pi 5 with 8GB of RAM.
Language | Compiler/Runtime | Build Flags | Runtime Features |
C | gcc 12.2.0 | -pipe -Wall -O3 -fomit-frame-pointer -march=native -fopenmp |
Native execution |
Java | javac 24.0.1 (GraalVM) | native-image --silent --gc=G1 -cp . -O3 -march=native |
Native execution with GraalVM |
JavaScript | N/A | N/A | Deno 2.3.3 (V8 13.7.152.6) |
TypeScript | N/A | N/A | Deno 2.3.3 (TypeScript 5.8.3) |
Ruby | N/A | N/A | Ruby 3.1.2p20 with YJIT |
Zig | zig 0.14 | -O ReleaseFast -lc |
Native execution |
Benchmark | C | Java | JavaScript/TypeScript | Ruby | Zig |
binarytrees | Standard C library | java.util.concurrent |
Deno standard library | Ruby standard library | Zig standard library |
fannkuchredux | OpenMP | java.util.concurrent |
Deno standard library | Ruby standard library | Zig standard library |
fasta | Standard C library | Java standard library | TextEncoder , Deno I/O APIs |
Ruby standard library | Zig standard library |
knucleotide | Custom hash table (khash.h ), OpenMP |
Java collections, concurrency | TextDecoder , Deno I/O APIs |
Ruby standard library, parallel execution | Zig standard library, custom Map implementation |
mandelbrot | OpenMP | java.util.concurrent |
Deno I/O APIs, navigator.hardwareConcurrency |
Ruby standard library | Zig standard library |
nbody | Standard C library, math library | Java standard library | Deno standard library | Ruby standard library | Zig standard library |
pidigits | GMP library (-lgmp ) |
java.math.BigInteger |
JavaScript BigInt | Ruby standard library | Zig standard library |
regexredux | PCRE2 library (-lpcre2-8 ) |
java.util.regex , java.util.concurrent |
JavaScript RegExp, Deno I/O APIs | Ruby Regexp | Zig standard library |
reversecomplement | Standard C library | Java standard library | TextDecoder , Deno I/O APIs |
Ruby standard library | Zig standard library |
spectralnorm | Standard C library, math library | Java standard library | Deno standard library | Ruby standard library | Zig standard library |
There are multiple steps needed to run the benchmarks.
The measure_power.py
script is used to measure the power consumption of the program.
But it was created to run while having a Prometheus server running in the background - so that the power consumption can be measured over time.
To get Prometheus to work, please follow the instructions on their website here.
Please look at Language Dependencies and Benchmark-specific dependencies for more information on the dependencies used to run each benchmark.
You also need to create an input folder with txt files generated by running fasta with:
100000001
5000000
25000000
and name them, respectively:
revcomp-input100000001.txt
regexredux-input5000000.txt
knucleotide-input25000000.txt
To run the measure_power.py
script, run the following commands (we have only run it with Python 3.11):
python3 -m .venv venv
source venv/bin/activate
pip install -r requirements.txt
Then run the script with the following command:
python3 measure_power.py
A csv file will be created named energy_results.csv
.
Run the following command to create visualizations, and a LaTeX table of the results:
python3 visualize.py
This will create the following files:
build_energy_comparison.png
relative_run_energy.png
run_energy_comparison.png
total_energy_comparison.png
energy_usage_tables.tex