Skip to content

Commit ebe5e75

Browse files
committed
ch3: add exercise3.8
1 parent e688da8 commit ebe5e75

File tree

3 files changed

+128
-1
lines changed

3 files changed

+128
-1
lines changed

ch3/exercise3.8/mandelbrot.go

Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
package mandelbrot
2+
3+
import (
4+
"image/color"
5+
"math"
6+
"math/big"
7+
"math/cmplx"
8+
)
9+
10+
func mandelbrot64(z complex128) color.Color {
11+
const iterations = 200
12+
const contrast = 15
13+
var v complex64
14+
for n := uint8(0); n < iterations; n++ {
15+
v = v*v + complex64(z)
16+
if cmplx.Abs(complex128(v)) > 2 {
17+
if n > 50 {
18+
return color.RGBA{100, 0, 0, 255}
19+
}
20+
scale := math.Log(float64(n)) / math.Log(float64(iterations))
21+
return color.RGBA{0, 0, 255 - uint8(scale*255), 255}
22+
}
23+
}
24+
return color.Black
25+
}
26+
27+
func mandelbrot128(z complex128) color.Color {
28+
const iterations = 200
29+
const contrast = 15
30+
var v complex128
31+
for n := uint8(0); n < iterations; n++ {
32+
v = v*v + z
33+
if cmplx.Abs(v) > 2 {
34+
if n > 50 {
35+
return color.RGBA{100, 0, 0, 255}
36+
}
37+
scale := math.Log(float64(n)) / math.Log(float64(iterations))
38+
return color.RGBA{0, 0, 255 - uint8(scale*255), 255}
39+
}
40+
}
41+
return color.Black
42+
}
43+
44+
func mandelbrotBigFloat(z complex128) color.Color {
45+
const iterations = 200
46+
const contrast = 15
47+
zR := (&big.Float{}).SetFloat64(real(z))
48+
zI := (&big.Float{}).SetFloat64(imag(z))
49+
var vR, vI = &big.Float{}, &big.Float{}
50+
for i := uint8(0); i < iterations; i++ {
51+
vR2, vI2 := &big.Float{}, &big.Float{}
52+
vR2.Mul(vR, vR).Sub(vR2, (&big.Float{}).Mul(vI, vI)).Add(vR2, zR)
53+
vI2.Mul(vR, vI).Mul(vI2, big.NewFloat(2)).Add(vI2, zI)
54+
vR, vI = vR2, vI2
55+
squareSum := &big.Float{}
56+
squareSum.Mul(vR, vR).Add(squareSum, (&big.Float{}).Mul(vI, vI))
57+
if squareSum.Cmp(big.NewFloat(4)) == 1 {
58+
if i > 50 {
59+
return color.RGBA{100, 0, 0, 255}
60+
}
61+
scale := math.Log(float64(i)) / math.Log(float64(iterations))
62+
return color.RGBA{0, 0, 255 - uint8(scale*255), 255}
63+
}
64+
}
65+
return color.Black
66+
}
67+
68+
func mandelbrotBigRat(z complex128) color.Color {
69+
const iterations = 200
70+
const contrast = 15
71+
zR := (&big.Rat{}).SetFloat64(real(z))
72+
zI := (&big.Rat{}).SetFloat64(imag(z))
73+
var vR, vI = &big.Rat{}, &big.Rat{}
74+
for i := uint8(0); i < iterations; i++ {
75+
vR2, vI2 := &big.Rat{}, &big.Rat{}
76+
vR2.Mul(vR, vR).Sub(vR2, (&big.Rat{}).Mul(vI, vI)).Add(vR2, zR)
77+
vI2.Mul(vR, vI).Mul(vI2, big.NewRat(2, 1)).Add(vI2, zI)
78+
vR, vI = vR2, vI2
79+
squareSum := &big.Rat{}
80+
squareSum.Mul(vR, vR).Add(squareSum, (&big.Rat{}).Mul(vI, vI))
81+
if squareSum.Cmp(big.NewRat(4, 1)) == 1 {
82+
if i > 50 {
83+
return color.RGBA{100, 0, 0, 255}
84+
}
85+
scale := math.Log(float64(i)) / math.Log(float64(iterations))
86+
return color.RGBA{0, 0, 255 - uint8(scale*255), 255}
87+
}
88+
}
89+
return color.Black
90+
}

ch3/exercise3.8/mandelbrot_test.go

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
package mandelbrot
2+
3+
import (
4+
"image/color"
5+
"testing"
6+
)
7+
8+
func bench(b *testing.B, f func(complex128) color.Color) {
9+
for i := 0; i < b.N; i++ {
10+
f(complex(float64(i), float64(i)))
11+
}
12+
}
13+
14+
func BenchmarkMandelbrotComplex64(b *testing.B) {
15+
bench(b, mandelbrot64)
16+
}
17+
18+
func BenchmarkMandelbrotComplex128(b *testing.B) {
19+
bench(b, mandelbrot128)
20+
}
21+
22+
func BenchmarkMandelbrotBigFloat(b *testing.B) {
23+
bench(b, mandelbrotBigFloat)
24+
}
25+
26+
func BenchmarkMandelbrotBigRat(b *testing.B) {
27+
bench(b, mandelbrotBigRat)
28+
}
29+
30+
/*
31+
goos: darwin
32+
goarch: amd64
33+
pkg: github.com/linehk/gopl/ch3/exercise3.8
34+
BenchmarkMandelbrotComplex64-8 20000000 57.9 ns/op
35+
BenchmarkMandelbrotComplex128-8 20000000 56.5 ns/op
36+
BenchmarkMandelbrotBigFloat-8 2000000 590 ns/op
37+
BenchmarkMandelbrotBigRat-8 1000000 1334 ns/op
38+
*/

ch3/exercise3.8_TODO/main.go

Lines changed: 0 additions & 1 deletion
This file was deleted.

0 commit comments

Comments
 (0)