diff options
Diffstat (limited to 'Week15 Mandelbrot/src/com/camilstaps/mandelbrot/MandelbrotFractal.java')
-rw-r--r-- | Week15 Mandelbrot/src/com/camilstaps/mandelbrot/MandelbrotFractal.java | 121 |
1 files changed, 121 insertions, 0 deletions
diff --git a/Week15 Mandelbrot/src/com/camilstaps/mandelbrot/MandelbrotFractal.java b/Week15 Mandelbrot/src/com/camilstaps/mandelbrot/MandelbrotFractal.java new file mode 100644 index 0000000..e0c0520 --- /dev/null +++ b/Week15 Mandelbrot/src/com/camilstaps/mandelbrot/MandelbrotFractal.java @@ -0,0 +1,121 @@ +/* + * The MIT License (MIT) + * + * Copyright (c) 2015 Camil Staps <info@camilstaps.nl> + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ +package com.camilstaps.mandelbrot; + +import java.util.HashMap; +import java.util.Map; + +/** + * Class for calculating Mandelbrot numbers + * By remembering seen numbers, we can significantly decrease calculation time + * + * @author Camil Staps + */ +public class MandelbrotFractal { + + /** + * Storage for previously calculated numbers + */ + private static final Map<Point,Result> mandelNumbers = new HashMap<>(); + + public static int mandelNumber(double x, double y, int repetitions) { + Point p = new Point(x, y); + return mandelNumber(p, repetitions); + } + + public static int mandelNumber(Point p, int repetitions) { + if (mandelNumbers.containsKey(p)) { + Result result = mandelNumbers.get(p); + if (repetitions < result.repetitions || + result.mandelNumber < result.repetitions) { + return result.mandelNumber; + } else { + calculateMandelNumber(p, repetitions, result); + return result.mandelNumber; + } + } else { + Result result = calculateMandelNumber(p, repetitions); + mandelNumbers.put(p, result); + return result.mandelNumber; + } + } + + protected static Result calculateMandelNumber(Point p, int repetitions) { + Result start = new Result(); + start.x = p.x; + start.y = p.y; + calculateMandelNumber(p, repetitions, start); + return start; + } + + protected static void calculateMandelNumber(Point p, int repetitions, Result start) { + int n = start.repetitions; + + while (start.x * start.x + start.y * start.y <= 4 && n <= repetitions) { + double new_x = start.x * start.x - start.y * start.y + p.x; + start.y = 2 * start.x * start.y + p.y; + start.x = new_x; + n++; + } + + start.mandelNumber = n; + } + + public static class Point { + double x, y; + + public Point(double x, double y) { + this.x = x; + this.y = y; + } + + @Override + public boolean equals(Object another) { + if (another == null || another.getClass() != Point.class) { + return false; + } + Point that = (Point) another; + return that.x == x && that.y == y; + } + + @Override + public int hashCode() { + int hash = 7; + hash = 97 * hash + (int) (Double.doubleToLongBits(this.x) ^ (Double.doubleToLongBits(this.x) >>> 32)); + hash = 97 * hash + (int) (Double.doubleToLongBits(this.y) ^ (Double.doubleToLongBits(this.y) >>> 32)); + return hash; + } + + @Override + public String toString() { + return String.format("(%f,%f)", x, y); + } + } + + protected static class Result { + int mandelNumber = -1, repetitions = -1; + double x, y; + } + +} |