Last active
September 20, 2021 08:25
-
-
Save highfestiva/97ad0900dc39f754711f81a9bb0dac81 to your computer and use it in GitHub Desktop.
nim 1.4.8 port of the java languange shootout version
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# Ported from https://benchmarksgame-team.pages.debian.net/benchmarksgame/program/mandelbrot-java-2.html | |
# Nim is about 29% faster than the Java 11 version. | |
# | |
# Build: nim c --threads:on -d:release --passC:-march=native mandelbrot2.nim && time ./mandelbrot2 16000 > m.pbm | |
# real 0m1.096s | |
# user 0m11.859s | |
# sys 0m0.141s | |
{.experimental, checks:off, optimization: speed.} | |
import bitops, os, strutils, threadpool | |
func getByte(x, y: int, Cib, Crb: seq[float]): uint8 {.inline.} = | |
var res: uint8 = 0'u8 | |
for i in countup(0, 8-2, 2): | |
let z = x + 1 | |
var Zr1 = Crb[x+i] | |
var Zi1 = Cib[y] | |
var Zr2 = Crb[x+i+1] | |
var Zi2 = Cib[y] | |
var b: uint8 = 0x03'u8 | |
for _ in 0..<49: | |
let nZr1 = Zr1*Zr1-Zi1*Zi1+Crb[z] | |
let nZi1 = Zr1*Zi1+Zr1*Zi1+Cib[y] | |
Zr1 = nZr1 | |
Zi1 = nZi1 | |
let nZr2 = Zr2*Zr2-Zi2*Zi2+Crb[z+1] | |
let nZi2 = Zr2*Zi2+Zr2*Zi2+Cib[y] | |
Zr2 = nZr2 | |
Zi2 = nZi2 | |
if Zr1*Zr1+Zi1*Zi1 > 4: | |
b.clearMask(2'u8) | |
if b == 0'u8: break | |
if Zr2*Zr2+Zi2*Zi2 > 4: | |
b.clearMask(1'u8) | |
if b == 0'u8: break | |
res = res * 4 + b | |
return res | |
func runRow(bw, y: int, buf: var seq[uint8], Cib, Crb: seq[float]) {.inline.} = | |
let b = bw * y | |
for xb in 0..<bw: | |
buf[b+xb] = getByte(xb*8, y, Cib, Crb) | |
proc main() = | |
let N = if commandLineParams().len >= 1: parseInt(commandLineParams()[0]) else: 6000 | |
var Cib = newSeq[float](N+7) | |
var Crb = newSeq[float](N+7) | |
let invN = 2 / N | |
for i in 0..<N: | |
let f = float(i) | |
Cib[i] = f*invN-1.0 | |
Crb[i] = f*invN-1.5 | |
let bw = (N+7) div 8 | |
var buf = newSeq[uint8](N*bw) | |
parallel: | |
for y in 0..<N: | |
spawn runRow(bw, y, buf, Cib, Crb) | |
stdout.write("P4\n$1 $2\n" % [$N, $N]) | |
discard stdout.writeBuffer(addr buf[0], buf.len) | |
main() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment