Math-Random-MT-1.17/0000755000175000017500000000000012626126066014316 5ustar flofloooflofloooMath-Random-MT-1.17/MT.xs0000644000175000017500000000247612265206403015214 0ustar floflooofloflooo#include "EXTERN.h" #include "perl.h" #include "XSUB.h" #include "ppport.h" #include "mt.h" typedef struct mt * Math__Random__MT; void * U32ArrayPtr ( int n ) { SV * sv = sv_2mortal( NEWSV( 0, n*sizeof(U32) ) ); return SvPVX(sv); } MODULE = Math::Random::MT PACKAGE = Math::Random::MT PREFIX = mt_ PROTOTYPES: DISABLE Math::Random::MT mt_init() CODE: RETVAL = mt_init(); OUTPUT: RETVAL void mt_init_seed(self, seed) Math::Random::MT self U32 seed CODE: mt_init_seed(self, seed); void mt_setup_array(self, array, ...) Math::Random::MT self; U32 * array = U32ArrayPtr( items ); PREINIT: U32 ix_array = 0; CODE: items--; while ( items--) { array[ix_array] = (U32)SvIV(ST(ix_array+1)); ix_array++; } mt_setup_array(self, (uint32_t*)array, ix_array); void mt_DESTROY(self) Math::Random::MT self CODE: mt_free(self); U32 mt_get_seed(self) Math::Random::MT self CODE: RETVAL = mt_get_seed(self); OUTPUT: RETVAL double mt_genrand(self) Math::Random::MT self CODE: RETVAL = mt_genrand(self); OUTPUT: RETVAL U32 mt_genirand(self) Math::Random::MT self CODE: RETVAL = mt_genirand(self); OUTPUT: RETVAL Math-Random-MT-1.17/MT.pm0000644000175000017500000001124312626125714015174 0ustar floflooofloflooopackage Math::Random::MT; use strict; use Carp; use DynaLoader; use vars qw( @ISA $VERSION ); my $gen = undef; @ISA = qw( DynaLoader ); $VERSION = '1.17'; bootstrap Math::Random::MT $VERSION; sub new { my ($class, @seeds) = @_; my $self = Math::Random::MT::init(); $self->set_seed(@seeds); return $self; } sub set_seed { my ($self, @seeds) = @_; @seeds > 1 ? $self->setup_array(@seeds) : $self->init_seed(defined $seeds[0] ? $seeds[0] : _rand_seed()); return $self->get_seed; } sub srand { my (@seeds) = @_; $gen = Math::Random::MT->new(@seeds); return $gen->get_seed; } sub rand { my ($self, $N) = @_; unless (ref $self) { $N = $self; Math::Random::MT::srand() unless defined $gen; $self = $gen; } return ($N || 1) * $self->genrand(); } sub irand { my ($self) = @_; unless (ref $self) { Math::Random::MT::srand() unless defined $gen; $self = $gen; } return $self->genirand(); } # Generate a random seed using the built-in PRNG. sub _rand_seed { my ($self) = @_; # Get a seed at random through Perl's CORE::rand(). We do not call # CORE::srand() to avoid altering the random numbers that other parts of # the running script might be using. The seeds obtained by rapid calls to # the _rand_seed() function are all different. return int(CORE::rand(2**32)); } sub import { no strict 'refs'; my $pkg = caller; foreach my $sym (@_) { if ($sym eq 'srand' || $sym eq 'rand' || $sym eq 'irand') { *{"${pkg}::$sym"} = \&$sym; } } } 1; __END__ =head1 NAME Math::Random::MT - The Mersenne Twister PRNG =head1 SYNOPSIS ## Object-oriented interface: use Math::Random::MT; $gen = Math::Random::MT->new() # or... $gen = Math::Random::MT->new($seed); # or... $gen = Math::Random::MT->new(@seeds); $seed = $gen->get_seed(); # seed used to generate the random numbers $rand = $gen->rand(42); # random number in the interval [0, 42) $dice = int($gen->rand(6)+1); # random integer between 1 and 6 $coin = $gen->rand() < 0.5 ? # flip a coin "heads" : "tails" $int = $gen->irand(); # random integer in [0, 2^32-1] ## Function-oriented interface: use Math::Random::MT qw(srand rand irand); # now use srand() and rand() as you usually do in Perl =head1 DESCRIPTION The Mersenne Twister is a pseudorandom number generator developed by Makoto Matsumoto and Takuji Nishimura. It is described in their paper at . This algorithm has a very uniform distribution and is good for modelling purposes but do not use it for cryptography. This module implements two interfaces: =head2 Object-oriented interface =over =item new() Creates a new generator that is automatically seeded based on gettimeofday. =item new($seed) Creates a new generator seeded with an unsigned 32-bit integer. =item new(@seeds) Creates a new generator seeded with an array of (up to 624) unsigned 32-bit integers. =item set_seed() Seeds the generator and returns the seed used. It takes the same arguments as I. =item get_seed() Retrieves the value of the seed used. =item rand($num) Behaves exactly like Perl's builtin rand(), returning a number uniformly distributed in [0, $num) ($num defaults to 1). =item irand() Returns a 32-bit integer, i.e. an integer uniformly distributed in [0, 2^32-1]. =back =head2 Function-oriented interface =over =item srand($seed) Behaves just like Perl's builtin srand(). As in Perl >= 5.14, the seed is returned. If you use this interface, it is strongly recommended that you call I explicitly, rather than relying on I to call it the first time it is used. =item rand($num) Behaves exactly like Perl's builtin rand(), returning a number uniformly distributed in [0, $num) ($num defaults to 1). =item irand() Returns a 32-bit integer, i.e. an integer uniformly distributed in [0, 2^32-1]. =back =head1 SEE ALSO Data::Entropy =head1 ACKNOWLEDGEMENTS =over 4 =item Sean M. Burke For giving me the idea to write this module. =item Philip Newton For several useful patches. =item Florent Angly For implementing seed generation and retrieval. =back =head1 AUTHOR Abhijit Menon-Sen Copyright 2001 Abhijit Menon-Sen. All rights reserved. Based on the C implementation of MT19937 Copyright (C) 1997 - 2002, Makoto Matsumoto and Takuji Nishimura This software is distributed under a (three-clause) BSD-style license. See the LICENSE file in the distribution for details. Math-Random-MT-1.17/mt.h0000644000175000017500000000141312265206403015077 0ustar floflooofloflooo#ifndef _MATH_MT_H_ #define _MATH_MT_H_ #if defined(_MSC_VER) && (_MSC_VER < 1600) // for MS Visual Studio prior to 2010 typedef unsigned __int32 uint32_t; #elif defined(__linux__) || defined(__GLIBC__) || defined(__WIN32__) || defined(_MSC_VER) || defined(__APPLE__) || defined(__GNU__) #include #elif defined(__osf__) #include #else #include #endif enum { N = 624, M = 397 }; struct mt { uint32_t mt[N]; int mti; uint32_t seed; }; struct mt *mt_init(void); void mt_free(struct mt *self); uint32_t mt_get_seed(struct mt *self); void mt_init_seed(struct mt *self, uint32_t seed); void mt_setup_array(struct mt *self, uint32_t *array, int n); double mt_genrand(struct mt *self); uint32_t mt_genirand(struct mt *self); #endif Math-Random-MT-1.17/Makefile.PL0000644000175000017500000000056112265206403016263 0ustar floflooofloflooouse ExtUtils::MakeMaker; WriteMakefile( NAME => 'Math::Random::MT', OBJECT => 'MT.o _mt.o', VERSION_FROM => 'MT.pm', ABSTRACT_FROM => 'MT.pm', AUTHOR => 'Abhijit Menon-Sen', PREREQ_PM => { 'Test::More' => 0, 'Test::Number::Delta' => 0, }, LICENSE => 'bsd', ); Math-Random-MT-1.17/Changes0000644000175000017500000000542312626125705015614 0ustar floflooofloflooo1.17 2015-11-27 Florent Angly * Bugfix: giving a seed value of 0 was ignored (reported by Maxim Tyukov) 1.16 2012-08-06 Florent Angly * Fixed issue introduced in version 1.15 where rand() took no notice of argument and irand() did (bug #78200, reported by David Morel) * Migration of test suite to Test::More and Test::Number::Delta 1.15 2012-06-04 Florent Angly * Implemented irand() to draw random integers (bug #73298, feature requested by crew@cs.stanford.edu) * Fixed build failure on Hurd (bug #74165, reported and patched by Salvatore Bonaccorso) 1.14 2012-05-27 Florent Angly * Fixed compilation problems with nmake on Windows platforms (Florent Angly, bug #74984) * Fixed issues with random seed (bug #77343, solution suggested by Laurent Dami, fix implemented by Florent Angly) 1.13 2012-01-20 Abhijit Menon-Sen * New seed generation and retrieval mechanism by Florent Angly (bug #64640 on rt.cpan.org). 1.12 2010-09-29 Abhijit Menon-Sen * Fix OS X build failure reported by Daniel Barker and fixed by Tokuhiro Matsuno. 1.11 2010-05-08 Abhijit Menon-Sen * Fix tests broken by overly optimistic floating point comparison and long doubles in new releases of Perl. (Thanks to Salvatore Bonaccorso for the report and fix.) 1.10 2009-08-06 Abhijit Menon-Sen * Compile fix for MSVC, which has no stdint.h. (Thanks to Taro Nishino for the report and patch.) (I made a mistake releasing 1.09.) 1.08 2009-08-06 Abhijit Menon-Sen * BSD license * Compile fix for GNU/kFreeBSD from Cyril Brulebois (via Debian) 1.07 2007-01-12 Abhijit Menon-Sen * Add the Changes file to the MANIFEST, in addition to editing it each time. (Thanks to John M. Gamble.) There have been no changes in functionality since 1.03. 1.06 2007-01-11 Abhijit Menon-Sen * Minor POD fix from Steven Schubiger. 1.05 2007-01-11 Abhijit Menon-Sen * Mingw compile fix from Steffen Mueller. 1.04 2004-10-09 Abhijit Menon-Sen * Incorporated some compile fixes from Gordon Lack. (1.03 had only some documentation changes.) 1.02 2004-05-07 Abhijit Menon-Sen * Added support for seeding the random number generator with an array of numbers, as suggested by Philip M. Feldman. (1.01 was not released.) 1.00 2002-02-09 Abhijit Menon-Sen * First stable release. Math-Random-MT-1.17/MANIFEST0000644000175000017500000000050712626126066015451 0ustar floflooofloflooo_mt.c Changes LICENSE Makefile.PL MANIFEST This list of files mt.h MT.pm MT.xs ppport.h README t/1.t t/2.t t/3.t t/4.t t/5.t t/6.t t/7.t t/8.t t/9.t typemap META.yml Module YAML meta-data (added by MakeMaker) META.json Module JSON meta-data (added by MakeMaker) Math-Random-MT-1.17/typemap0000644000175000017500000000005212265206403015706 0ustar flofloooflofloooMath::Random::MT T_PTROBJ U32 * T_ARRAYMath-Random-MT-1.17/_mt.c0000644000175000017500000000530112265206403015231 0ustar floflooofloflooo#include "mt.h" #include #include /* This code is based on mt19937ar.c, written by Takuji Nishimura and Makoto Matsumoto (20020126). Further details are available at . REFERENCE M. Matsumoto and T. Nishimura, "Mersenne Twister: A 623-Dimensionally Equidistributed Uniform Pseudo-Random Number Generator", ACM Transactions on Modeling and Computer Simulation, Vol. 8, No. 1, January 1998, pp 3--30. */ struct mt *mt_init(void) { struct mt *self = malloc(sizeof(struct mt)); return self; } void mt_free(struct mt *self) { free(self); } uint32_t mt_get_seed(struct mt *self) { return self->seed; } void mt_init_seed(struct mt *self, uint32_t seed) { int i; uint32_t *mt; mt = self->mt; mt[0] = seed & 0xffffffff; for ( i = 1; i < N; i++ ) mt[i] = 1812433253 * (mt[i-1]^(mt[i-1]>>30)) + i; self->mti = N; self->seed = mt[0]; } void mt_setup_array(struct mt *self, uint32_t *array, int n) { int i, j, k; uint32_t *mt; mt_init_seed( self, 19650218UL ); i = 1; j = 0; k = ( N > n ? N : n ); mt = self->mt; for (; k; k--) { mt[i] = (mt[i] ^ ((mt[i-1] ^ (mt[i-1] >> 30)) * 1664525UL)) + array[j] + j; i++; j++; if (i>=N) { mt[0] = mt[N-1]; i=1; } if (j>=n) j=0; } for (k=N-1; k; k--) { mt[i] = (mt[i] ^ ((mt[i-1] ^ (mt[i-1] >> 30)) * 1566083941UL)) - i; i++; if (i>=N) { mt[0] = mt[N-1]; i=1; } } mt[0] = 0x80000000UL; } /* Returns a pseudorandom number which is uniformly distributed in [0,1) */ double mt_genrand(struct mt *self) { return mt_genirand(self)*(1.0/4294967296.0); } /* Returns a pseudorandom 32-bit integer uniformly distributed in [0,2^32-1] */ uint32_t mt_genirand(struct mt *self) { int kk; uint32_t y; static uint32_t mag01[2] = {0x0, 0x9908b0df}; static const uint32_t UP_MASK = 0x80000000, LOW_MASK = 0x7fffffff; if (self->mti >= N) { for (kk = 0; kk < N-M; kk++) { y = (self->mt[kk] & UP_MASK) | (self->mt[kk+1] & LOW_MASK); self->mt[kk] = self->mt[kk+M] ^ (y >> 1) ^ mag01[y & 1]; } for (; kk < N-1; kk++) { y = (self->mt[kk] & UP_MASK) | (self->mt[kk+1] & LOW_MASK); self->mt[kk] = self->mt[kk+(M-N)] ^ (y >> 1) ^ mag01[y & 1]; } y = (self->mt[N-1] & UP_MASK) | (self->mt[0] & LOW_MASK); self->mt[N-1] = self->mt[M-1] ^ (y >> 1) ^ mag01[y & 1]; self->mti = 0; } y = self->mt[self->mti++]; y ^= y >> 11; y ^= y << 7 & 0x9d2c5680; y ^= y << 15 & 0xefc60000; y ^= y >> 18; return y; } Math-Random-MT-1.17/ppport.h0000644000175000017500000001716312265206403016014 0ustar floflooofloflooo #ifndef _P_P_PORTABILITY_H_ #define _P_P_PORTABILITY_H_ /* Perl/Pollution/Portability Version 1.0007 */ /* Copyright (C) 1999, Kenneth Albanowski. This code may be used and distributed under the same license as any version of Perl. */ /* For the latest version of this code, please retreive the Devel::PPPort module from CPAN, contact the author at , or check with the Perl maintainers. */ /* If you needed to customize this file for your project, please mention your changes, and visible alter the version number. */ /* In order for a Perl extension module to be as portable as possible across differing versions of Perl itself, certain steps need to be taken. Including this header is the first major one, then using dTHR is all the appropriate places and using a PL_ prefix to refer to global Perl variables is the second. */ /* If you use one of a few functions that were not present in earlier versions of Perl, please add a define before the inclusion of ppport.h for a static include, or use the GLOBAL request in a single module to produce a global definition that can be referenced from the other modules. Function: Static define: Extern define: newCONSTSUB() NEED_newCONSTSUB NEED_newCONSTSUB_GLOBAL */ /* To verify whether ppport.h is needed for your module, and whether any special defines should be used, ppport.h can be run through Perl to check your source code. Simply say: perl -x ppport.h *.c *.h *.xs foo/*.c [etc] The result will be a list of patches suggesting changes that should at least be acceptable, if not necessarily the most efficient solution, or a fix for all possible problems. It won't catch where dTHR is needed, and doesn't attempt to account for global macro or function definitions, nested includes, typemaps, etc. In order to test for the need of dTHR, please try your module under a recent version of Perl that has threading compiled-in. */ /* #!/usr/bin/perl @ARGV = ("*.xs") if !@ARGV; %badmacros = %funcs = %macros = (); $replace = 0; foreach () { $funcs{$1} = 1 if /Provide:\s+(\S+)/; $macros{$1} = 1 if /^#\s*define\s+([a-zA-Z0-9_]+)/; $replace = $1 if /Replace:\s+(\d+)/; $badmacros{$2}=$1 if $replace and /^#\s*define\s+([a-zA-Z0-9_]+).*?\s+([a-zA-Z0-9_]+)/; $badmacros{$1}=$2 if /Replace (\S+) with (\S+)/; } foreach $filename (map(glob($_),@ARGV)) { unless (open(IN, "<$filename")) { warn "Unable to read from $file: $!\n"; next; } print "Scanning $filename...\n"; $c = ""; while () { $c .= $_; } close(IN); $need_include = 0; %add_func = (); $changes = 0; $has_include = ($c =~ /#.*include.*ppport/m); foreach $func (keys %funcs) { if ($c =~ /#.*define.*\bNEED_$func(_GLOBAL)?\b/m) { if ($c !~ /\b$func\b/m) { print "If $func isn't needed, you don't need to request it.\n" if $changes += ($c =~ s/^.*#.*define.*\bNEED_$func\b.*\n//m); } else { print "Uses $func\n"; $need_include = 1; } } else { if ($c =~ /\b$func\b/m) { $add_func{$func} =1 ; print "Uses $func\n"; $need_include = 1; } } } if (not $need_include) { foreach $macro (keys %macros) { if ($c =~ /\b$macro\b/m) { print "Uses $macro\n"; $need_include = 1; } } } foreach $badmacro (keys %badmacros) { if ($c =~ /\b$badmacro\b/m) { $changes += ($c =~ s/\b$badmacro\b/$badmacros{$badmacro}/gm); print "Uses $badmacros{$badmacro} (instead of $badmacro)\n"; $need_include = 1; } } if (scalar(keys %add_func) or $need_include != $has_include) { if (!$has_include) { $inc = join('',map("#define NEED_$_\n", sort keys %add_func)). "#include \"ppport.h\"\n"; $c = "$inc$c" unless $c =~ s/#.*include.*XSUB.*\n/$&$inc/m; } elsif (keys %add_func) { $inc = join('',map("#define NEED_$_\n", sort keys %add_func)); $c = "$inc$c" unless $c =~ s/^.*#.*include.*ppport.*$/$inc$&/m; } if (!$need_include) { print "Doesn't seem to need ppport.h.\n"; $c =~ s/^.*#.*include.*ppport.*\n//m; } $changes++; } if ($changes) { open(OUT,">/tmp/ppport.h.$$"); print OUT $c; close(OUT); open(DIFF, "diff -u $filename /tmp/ppport.h.$$|"); while () { s!/tmp/ppport\.h\.$$!$filename.patched!; print STDOUT; } close(DIFF); unlink("/tmp/ppport.h.$$"); } else { print "Looks OK\n"; } } __DATA__ */ #ifndef PERL_REVISION # ifndef __PATCHLEVEL_H_INCLUDED__ # include "patchlevel.h" # endif # ifndef PERL_REVISION # define PERL_REVISION (5) /* Replace: 1 */ # define PERL_VERSION PATCHLEVEL # define PERL_SUBVERSION SUBVERSION /* Replace PERL_PATCHLEVEL with PERL_VERSION */ /* Replace: 0 */ # endif #endif #define PERL_BCDVERSION ((PERL_REVISION * 0x1000000L) + (PERL_VERSION * 0x1000L) + PERL_SUBVERSION) #ifndef ERRSV # define ERRSV perl_get_sv("@",FALSE) #endif #if (PERL_VERSION < 4) || ((PERL_VERSION == 4) && (PERL_SUBVERSION <= 5)) /* Replace: 1 */ # define PL_sv_undef sv_undef # define PL_sv_yes sv_yes # define PL_sv_no sv_no # define PL_na na # define PL_stdingv stdingv # define PL_hints hints # define PL_curcop curcop # define PL_curstash curstash # define PL_copline copline # define PL_Sv Sv /* Replace: 0 */ #endif #ifndef dTHR # ifdef WIN32 # define dTHR extern int Perl___notused # else # define dTHR extern int errno # endif #endif #ifndef boolSV # define boolSV(b) ((b) ? &PL_sv_yes : &PL_sv_no) #endif #ifndef gv_stashpvn # define gv_stashpvn(str,len,flags) gv_stashpv(str,flags) #endif #ifndef newSVpvn # define newSVpvn(data,len) ((len) ? newSVpv ((data), (len)) : newSVpv ("", 0)) #endif #ifndef newRV_inc /* Replace: 1 */ # define newRV_inc(sv) newRV(sv) /* Replace: 0 */ #endif #ifndef newRV_noinc # ifdef __GNUC__ # define newRV_noinc(sv) \ ({ \ SV *nsv = (SV*)newRV(sv); \ SvREFCNT_dec(sv); \ nsv; \ }) # else # if defined(CRIPPLED_CC) || defined(USE_THREADS) static SV * newRV_noinc (SV * sv) { SV *nsv = (SV*)newRV(sv); SvREFCNT_dec(sv); return nsv; } # else # define newRV_noinc(sv) \ ((PL_Sv=(SV*)newRV(sv), SvREFCNT_dec(sv), (SV*)PL_Sv) # endif # endif #endif /* Provide: newCONSTSUB */ /* newCONSTSUB from IO.xs is in the core starting with 5.004_63 */ #if (PERL_VERSION < 4) || ((PERL_VERSION == 4) && (PERL_SUBVERSION < 63)) #if defined(NEED_newCONSTSUB) static #else extern void newCONSTSUB _((HV * stash, char * name, SV *sv)); #endif #if defined(NEED_newCONSTSUB) || defined(NEED_newCONSTSUB_GLOBAL) void newCONSTSUB(stash,name,sv) HV *stash; char *name; SV *sv; { U32 oldhints = PL_hints; HV *old_cop_stash = PL_curcop->cop_stash; HV *old_curstash = PL_curstash; line_t oldline = PL_curcop->cop_line; PL_curcop->cop_line = PL_copline; PL_hints &= ~HINT_BLOCK_SCOPE; if (stash) PL_curstash = PL_curcop->cop_stash = stash; newSUB( #if (PERL_VERSION < 3) || ((PERL_VERSION == 3) && (PERL_SUBVERSION < 22)) /* before 5.003_22 */ start_subparse(), #else # if (PERL_VERSION == 3) && (PERL_SUBVERSION == 22) /* 5.003_22 */ start_subparse(0), # else /* 5.003_23 onwards */ start_subparse(FALSE, 0), # endif #endif newSVOP(OP_CONST, 0, newSVpv(name,0)), newSVOP(OP_CONST, 0, &PL_sv_no), /* SvPV(&PL_sv_no) == "" -- GMB */ newSTATEOP(0, Nullch, newSVOP(OP_CONST, 0, sv)) ); PL_hints = oldhints; PL_curcop->cop_stash = old_cop_stash; PL_curstash = old_curstash; PL_curcop->cop_line = oldline; } #endif #endif /* newCONSTSUB */ #endif /* _P_P_PORTABILITY_H_ */ Math-Random-MT-1.17/LICENSE0000644000175000017500000000303212265206403015312 0ustar flofloooflofloooCopyright (C) 1997 - 2002, Makoto Matsumoto and Takuji Nishimura, Copyright 2001 Abhijit Menon-Sen , All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: 1. Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. 2. Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. 3. The names of its contributors may not be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. Math-Random-MT-1.17/t/0000755000175000017500000000000012626126066014561 5ustar flofloooflofloooMath-Random-MT-1.17/t/1.t0000644000175000017500000000136012626125173015104 0ustar floflooofloflooouse strict; use Test::More; use Test::Number::Delta within => 1e-14; BEGIN { use_ok('Math::Random::MT'); } # Test that the OO interface works ok my $gen = Math::Random::MT->new(5489); isa_ok $gen, 'Math::Random::MT'; delta_ok $gen->rand(), 0.814723691903055; delta_ok $gen->rand(), 0.135477004107088; delta_ok $gen->irand(), 3890346734; delta_ok $gen->irand(), 3586334585; delta_ok $gen->rand(10), 1.269868118688464, 'rand() takes a multiplier as argument'; delta_ok $gen->rand(10), 9.688677710946649; delta_ok $gen->irand(123), 3922919429, 'irand() takes no argument'; # given argument does nothing delta_ok $gen->irand(123), 949333985; ok $gen = Math::Random::MT->new(0), '0 is a valid seed'; is $gen->get_seed(), 0; done_testing(); Math-Random-MT-1.17/t/7.t0000644000175000017500000000321012265206403015101 0ustar floflooofloflooouse strict; use Test::More; use Test::Number::Delta within => 1e-14; BEGIN { use_ok('Math::Random::MT'); } # OO interface # Test the ability to automatically generate a seed, return it, and reproduce # the same series of random number by specifying this seed manually. my ($gen, $autoseed, $num1, $num2, $num3, $num4, $num5, $num6, $int1, $int2, $int3, $int4, $int5, $int6); # Generate a series of 6 random numbers using an autogenerated seed ok $gen = Math::Random::MT->new(); ok $num1 = $gen->rand(); ok $num2 = $gen->rand(); ok $num3 = $gen->rand(); ok $int1 = $gen->irand(); ok $int2 = $gen->irand(); ok $int3 = $gen->irand(); ok $autoseed = $gen->get_seed(); # Generate a series of 6 random numbers the using same seed value but manually specified ok $gen = Math::Random::MT->new($autoseed); ok $num4 = $gen->rand(); ok $num5 = $gen->rand(); ok $num6 = $gen->rand(); ok $int4 = $gen->irand(); ok $int5 = $gen->irand(); ok $int6 = $gen->irand(); # Both series of number should be the same delta_ok $num1, $num4; delta_ok $num2, $num5; delta_ok $num3, $num6; delta_ok $int1, $int4; delta_ok $int2, $int5; delta_ok $int3, $int6; # Generate a series of 6 random numbers the using same seed value but manually specified ok $gen = Math::Random::MT->new(); delta_ok $gen->set_seed($autoseed), $autoseed; ok $num4 = $gen->rand(); ok $num5 = $gen->rand(); ok $num6 = $gen->rand(); ok $int4 = $gen->irand(); ok $int5 = $gen->irand(); ok $int6 = $gen->irand(); # Both series of number should be the same delta_ok $num1, $num4; delta_ok $num2, $num5; delta_ok $num3, $num6; delta_ok $int1, $int4; delta_ok $int2, $int5; delta_ok $int3, $int6; done_testing(); Math-Random-MT-1.17/t/3.t0000644000175000017500000000130612265206403015101 0ustar floflooofloflooouse strict; use Test::More; BEGIN { use_ok('Math::Random::MT', qw(srand rand irand)); } my ($num1, $num2); ok srand; # explicit srand, but without number eval { $num1 = rand; }; is $@, '', '$@ should be empty after rand() but it\'s: '.$@; isnt $num1, undef; cmp_ok $num1, '>=', 0; cmp_ok $num1, '<', 1; # rand without argument is like rand(1) eval { $num2 = rand; }; is $@, '', '$@ should also be empty the second time rand() is called'; isnt $num1, $num2; eval { $num1 = irand; }; is $@, '', '$@ should be empty after rand()'; isnt $num1, undef; cmp_ok $num1, '>=', 0; eval { $num2 = irand; }; is $@, '', '$@ should also be empty the second time rand() is called'; isnt $num1, $num2; done_testing(); Math-Random-MT-1.17/t/6.t0000644000175000017500000000047512265206403015112 0ustar floflooofloflooouse strict; use Test::More; use Test::Number::Delta within => 1e-14; BEGIN { use_ok('Math::Random::MT'); } # Check that we can use an array to seed the generator. my $gen; ok $gen = Math::Random::MT->new(1, 2, 3, 4); delta_ok $gen->rand(1), 0.67886575916782; delta_ok $gen->irand, 1022996879; done_testing(); Math-Random-MT-1.17/t/5.t0000644000175000017500000000101712265206403015102 0ustar floflooofloflooouse strict; use Test::More; use Test::Number::Delta within => 1e-14; BEGIN { use_ok('Math::Random::MT'); } # OO interface # Check that we can use an array to seed the generator. my $gen; ok $gen = Math::Random::MT->new(1, 2, 3, 4); delta_ok $gen->rand(1), 0.67886575916782; delta_ok $gen->irand, 1022996879; # high value seeds broke initial implementation of mt_setup_array() ok $gen = Math::Random::MT->new(1, 2, 3, 2**31); delta_ok $gen->rand(1), 0.336814725538716; delta_ok $gen->irand, 1615524784; done_testing(); Math-Random-MT-1.17/t/2.t0000644000175000017500000000123112626125246015103 0ustar floflooofloflooouse strict; use Test::More; use Test::Number::Delta within => 1e-14; BEGIN { use_ok('Math::Random::MT', qw(srand rand irand)); } # Test that functional interface results are identical to that of OO interface ok srand(5489); delta_ok rand(), 0.814723691903055; delta_ok rand(), 0.135477004107088; delta_ok irand(), 3890346734; delta_ok irand(), 3586334585; delta_ok rand(10), 1.269868118688464, 'rand() takes a multiplier as argument'; delta_ok rand(10), 9.688677710946649; delta_ok irand(123), 3922919429, 'irand() takes no argument'; # given argument does nothing delta_ok irand(123), 949333985; is srand(0), 0, '0 is a valid seed'; done_testing(); Math-Random-MT-1.17/t/8.t0000644000175000017500000000201012265206403015077 0ustar floflooofloflooouse strict; use Test::More; use Test::Number::Delta within => 1e-14; BEGIN { use_ok('Math::Random::MT', qw(srand rand)); } # Functional interface # Test the ability to automatically generate a seed, return it, and reproduce # the same series of random number by specifying this seed manually. my ($autoseed, $num1, $num2, $num3, $num4, $num5, $num6, $int1, $int2, $int3, $int4, $int5, $int6); # Generate a series of 6 random numbers using an autogenerated seed ok $autoseed = srand(); ok $num1 = rand(); ok $num2 = rand(); ok $num3 = rand(); ok $int1 = rand(); ok $int2 = rand(); ok $int3 = rand(); # Generate a series of 6 random numbers the same seed value but manually specified ok srand($autoseed); ok $num4 = rand(); ok $num5 = rand(); ok $num6 = rand(); ok $int4 = rand(); ok $int5 = rand(); ok $int6 = rand(); # Both series of number should be the same delta_ok $num1, $num4; delta_ok $num2, $num5; delta_ok $num3, $num6; delta_ok $int1, $int4; delta_ok $int2, $int5; delta_ok $int3, $int6; done_testing(); Math-Random-MT-1.17/t/4.t0000644000175000017500000000132112265206403015077 0ustar floflooofloflooouse strict; use Test::More; BEGIN { use_ok('Math::Random::MT', qw(srand rand irand)); } # Check that it's possible to call rand() without srand() my ($num1, $num2); eval { $num1 = rand; }; is $@, '', '$@ should be empty after rand() but it\'s: '.$@; isnt $num1, undef; cmp_ok $num1, '>=', 0; cmp_ok $num1, '<', 1; # rand without argument is like rand(1) eval { $num2 = rand; }; is $@, '', '$@ should also be empty the second time rand() is called'; isnt $num1, $num2; eval { $num1 = irand; }; is $@, '', '$@ should be empty after rand()'; isnt $num1, undef; cmp_ok $num1, '>=', 0; eval { $num2 = irand; }; is $@, '', '$@ should also be empty the second time rand() is called'; isnt $num1, $num2; done_testing(); Math-Random-MT-1.17/t/9.t0000644000175000017500000000103512265206403015106 0ustar floflooofloflooouse strict; use Test::More; use Benchmark qw(timediff timestr); BEGIN { use_ok('Math::Random::MT', qw(srand)); } # Make sure that automatic seeds generated close in time are different. my ($autoseed1, $autoseed2, $autoseed3, $autoseed4); # Generate a series of 3 random numbers using an autogenerated seed ok $autoseed1 = srand(); ok $autoseed2 = srand(); ok $autoseed3 = srand(); ok $autoseed4 = srand(); cmp_ok $autoseed1, '!=', $autoseed2; cmp_ok $autoseed2, '!=', $autoseed3; cmp_ok $autoseed3, '!=', $autoseed4; done_testing(); Math-Random-MT-1.17/META.yml0000644000175000017500000000106612626126066015572 0ustar floflooofloflooo--- abstract: 'The Mersenne Twister PRNG' author: - 'Abhijit Menon-Sen' build_requires: ExtUtils::MakeMaker: '0' configure_requires: ExtUtils::MakeMaker: '0' dynamic_config: 1 generated_by: 'ExtUtils::MakeMaker version 6.98, CPAN::Meta::Converter version 2.150005' license: bsd meta-spec: url: http://module-build.sourceforge.net/META-spec-v1.4.html version: '1.4' name: Math-Random-MT no_index: directory: - t - inc requires: Test::More: '0' Test::Number::Delta: '0' version: '1.17' x_serialization_backend: 'CPAN::Meta::YAML version 0.012' Math-Random-MT-1.17/META.json0000644000175000017500000000167512626126066015750 0ustar floflooofloflooo{ "abstract" : "The Mersenne Twister PRNG", "author" : [ "Abhijit Menon-Sen" ], "dynamic_config" : 1, "generated_by" : "ExtUtils::MakeMaker version 6.98, CPAN::Meta::Converter version 2.150005", "license" : [ "bsd" ], "meta-spec" : { "url" : "http://search.cpan.org/perldoc?CPAN::Meta::Spec", "version" : "2" }, "name" : "Math-Random-MT", "no_index" : { "directory" : [ "t", "inc" ] }, "prereqs" : { "build" : { "requires" : { "ExtUtils::MakeMaker" : "0" } }, "configure" : { "requires" : { "ExtUtils::MakeMaker" : "0" } }, "runtime" : { "requires" : { "Test::More" : "0", "Test::Number::Delta" : "0" } } }, "release_status" : "stable", "version" : "1.17", "x_serialization_backend" : "JSON::PP version 2.27203" } Math-Random-MT-1.17/README0000644000175000017500000000624212265206403015173 0ustar flofloooflofloooNAME Math::Random::MT - The Mersenne Twister PRNG SYNOPSIS ## Object-oriented interface: use Math::Random::MT; $gen = Math::Random::MT->new() # or... $gen = Math::Random::MT->new($seed); # or... $gen = Math::Random::MT->new(@seeds); $seed = $gen->get_seed(); # seed used to generate the random numbers $rand = $gen->rand(42); # random number in the interval [0, 42) $dice = int($gen->rand(6)+1); # random integer between 1 and 6 $coin = $gen->rand() < 0.5 ? # flip a coin "heads" : "tails" $int = $gen->irand(); # random integer in [0, 2^32-1] ## Function-oriented interface: use Math::Random::MT qw(srand rand irand); # now use srand() and rand() as you usually do in Perl DESCRIPTION The Mersenne Twister is a pseudorandom number generator developed by Makoto Matsumoto and Takuji Nishimura. It is described in their paper at . This algorithm has a very uniform distribution and is good for modelling purposes but do not use it for cryptography. This module implements two interfaces: Object-oriented interface new() Creates a new generator that is automatically seeded based on gettimeofday. new($seed) Creates a new generator seeded with an unsigned 32-bit integer. new(@seeds) Creates a new generator seeded with an array of (up to 624) unsigned 32-bit integers. set_seed() Seeds the generator. It takes the same arguments as *new()*. get_seed() Retrieves the value of the seed used. rand($num) Behaves exactly like Perl's builtin rand(), returning a number uniformly distributed in [0, $num) ($num defaults to 1). irand() Returns a 32-bit integer, i.e. an integer uniformly distributed in [0, 2^32-1]. Function-oriented interface srand($seed) Behaves just like Perl's builtin srand(). As in Perl >= 5.14, the seed is returned. If you use this interface, it is strongly recommended that you call *srand()* explicitly, rather than relying on *rand()* to call it the first time it is used. rand($num) Behaves exactly like Perl's builtin rand(), returning a number uniformly distributed in [0, $num) ($num defaults to 1). irand() Returns a 32-bit integer, i.e. an integer uniformly distributed in [0, 2^32-1]. SEE ALSO Data::Entropy ACKNOWLEDGEMENTS Sean M. Burke For giving me the idea to write this module. Philip Newton For several useful patches. Florent Angly For implementing seed generation and retrieval. AUTHOR Abhijit Menon-Sen Copyright 2001 Abhijit Menon-Sen. All rights reserved. Based on the C implementation of MT19937 Copyright (C) 1997 - 2002, Makoto Matsumoto and Takuji Nishimura This software is distributed under a (three-clause) BSD-style license. See the LICENSE file in the distribution for details.