/* * Copyright 2010 OpenXcom Developers. * * This file is part of OpenXcom. * * OpenXcom is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * OpenXcom is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with OpenXcom. If not, see . */ #include "RNG.h" #define _USE_MATH_DEFINES #include #include #include namespace OpenXcom { namespace RNG { int _seed = 0; /** * Seeds the random generator with a new number. * Defaults to the current time if none is set. * @param seed New seed. */ void init(int seed) { if (seed == -1) { _seed = (int)time(NULL); } else { _seed = seed; } srand(_seed); } /** * Returns the last seed used by the generator. * @return Generator seed. */ int getSeed() { return _seed; } /** * Generates a random integer number within a certain range. * @param min Minimum number. * @param max Maximum number. * @return Generated number. */ int generate(int min, int max) { _seed = rand(); return (_seed % (max - min + 1) + min); } /** * Generates a random decimal number within a certain range. * @param min Minimum number. * @param max Maximum number. * @return Generated number. */ double generate(double min, double max) { _seed = rand(); return (_seed * (max - min) / RAND_MAX + min); } /** * Normal random variate generator * @param m mean * @param s standard deviation * @return normally distributed value. */ double boxMuller(double m, double s) { double y1; static double y2; static int use_last = 0; if (use_last) /* use value from previous call */ { y1 = y2; use_last = 0; } else { double x1, x2, w; do { x1 = 2.0 * generate(0.0, 1.0) - 1.0; x2 = 2.0 * generate(0.0, 1.0) - 1.0; w = x1 * x1 + x2 * x2; } while ( w >= 1.0 ); w = sqrt( (-2.0 * log( w ) ) / w ); y1 = x1 * w; y2 = x2 * w; use_last = 1; } return( m + y1 * s ); } } }