On Friday, 24 April 2015 at 11:39:14 UTC, John Colvin wrote:
On Friday, 24 April 2015 at 11:00:23 UTC, Chris wrote:
I tested the performance of three types of loops (see code below). It turns out that the fastest loop is the "plainLoop". Unless my examples are completely screwed up, the difference between "plainLoop" and the other two loops is gigantic (e.g.):

9 ms, 149 μs, and 4 hnsecs  // foreach (const ref w)
9 ms, 77 μs, and 8 hnsecs   // foreach (ref w)
1 ms, 183 μs, and 6 hnsecs  // foreach (w)

with -release -inline -O -boundscheck=off

8 ms, 492 μs, and 3 hnsecs
8 ms, 287 μs, and 1 hnsec
341 μs and 2 hnsecs

[compiler dmd v2.067.0, Linux Ubuntu, 64bit]


import std.datetime : benchmark, Duration;
import std.string : format;
import std.conv : to;
import std.stdio : writeln;

enum {
 string[] words = ["Hello", "world", "Ola", "mundo"],
}

void main() {
auto result = benchmark!(constLoop, refLoop, plainLoop)(100_000);
 writeln(to!Duration(result[0]));
 writeln(to!Duration(result[1]));
 writeln(to!Duration(result[2]));

}

void constLoop() {
 size_t cnt;
 foreach (const ref w; words)
   cnt += w.length;
}

void refLoop() {
 size_t cnt;
 foreach (ref w; words)
   cnt += w.length;
}

void plainLoop() {
 size_t cnt;
 foreach (w; words)
   cnt += w.length;
}

dmd's optimiser isn't great. GDC creates identical assembly for all three functions.

Rule of thumb: if you want high performance, use GDC or LDC.

Yeah, I figure. However, the gap is a serious issue for dmd, even if it's only a reference compiler.

Reply via email to