Wiki
Download
Manual
Eggs
API
Tests
Bugs
show
edit
history
You can edit this page using
wiki syntax
for markup.
Article contents:
[[tags: egg]] == SRFI 194 Random Data Generators [[toc:]] == Description A Chicken port of the reference implementation of [[http://srfi.schemers.org/srfi-194/srfi-194.html|SRFI 194]]. Whenever possible, this library uses implementations from Chicken's [[srfi-27]] egg. == Authors SRFI 194 authors: Shiro Kawai (design), Arvydas Silanskas (implementation), Linas Vepštas (implementation), and John Cowan (editor and shepherd) Chicken maintainer: Peter McGoron == Repository https://software.mcgoron.com/peter/srfi-194-egg == Requirements * [[r7rs]] * [[srfi-27]] * [[srfi-133]] * [[srfi-158]] == API The following is mostly copy-pasted from the SRFI, with some Chicken-specific notes. === Current Random Source <procedure>(current-random-source)</procedure> An [[r7rs]] or SRFI 39 parameter that provides the random source for all the procedures in this SRFI. Its initial value is default-random-source from [[srfi-27]]. Use parameterize to specify a dynamic scope in which a different [[srfi-27]] random source is used when creating new generators. The behavior of existing generators is not affected by changes to this parameter. Chicken note: This is the same parameter as the one exported from the [[srfi-27]] egg. <procedure>(with-random-source random-source thunk)</procedure> Binds {{current-random-source}} to {{random-source}} and then invokes {{thunk}}. <procedure>(make-random-source-generator i)</procedure> Returns a generator of random sources. Each invocation of the generator returns a new random source created by calling {{make-random-source}} ([[srfi-27]]). The new random source is passed to {{random-source-pseudo-randomize!}} with {{i}}, and successive integers {{j}} (starting with 0), before being returned. The random sources are guaranteed to be distinct as long as {{i}} and {{j}} are not too large and the generator is not called too many times. What counts as "too large/many" depends on the SRFI 27 implementation; the sample implementation works correctly if {{i < 2^63}} and {{j < 2^51}} and no more than {{2^76}} values are generated. === Uniform distributions These generators generate uniformly distributed values of various simple Scheme types. <procedure>(make-random-integer-generator lower-bound upper-bound)</procedure> Returns a generator of exact integers between {{lower-bound}} (inclusive) and {{upper-bound}} (exclusive) uniformly. It is an error if the bounds are not exact integers or if the specified interval is empty. Chicken note: this is implemented using {{make-uniform-random-integers}} from [[srfi-27]]. Note that {{make-uniform-random-integers}} takes two inclusive bounds, which is different from this interface. <procedure>(make-random-u1-generator)</procedure> <procedure>(make-random-u8-generator)</procedure> <procedure>(make-random-s8-generator)</procedure> <procedure>(make-random-u16-generator)</procedure> <procedure>(make-random-s16-generator)</procedure> <procedure>(make-random-u32-generator)</procedure> <procedure>(make-random-s32-generator)</procedure> <procedure>(make-random-u64-generator)</procedure> <procedure>(make-random-s64-generator)</procedure> These procedures return generators of exact integers in the ranges of 1-bit unsigned and 8, 16, 32, and 64-bit signed and unsigned values respectively. These values can be stored in the corresponding homogeneous vectors of [[srfi-160]] and [[srfi-178]]. <procedure>(clamp-real-number lower-bound upper-bound value)</procedure> Returns value clamped to be between {{lower-bound}} and {{upper-bound}}, inclusive. Note that this procedure works with either exact or inexact numbers, but will produce strange results with a mixture of the two. It is an error if the specified interval is empty. <procedure>(make-random-real-generator lower-bound upper-bound)</procedure> Returns a generator that generates inexact real numbers uniformly. (Note that this is not the same as returning all possible IEEE floats within the stated range uniformly.) The procedure returns reals between {{lower-bound}} and {{upper-bound}}, both inclusive. The similar procedure random-real in SRFI 27 uses the exclusive bounds 0.0 and 1.0. It is an error if the specified interval is empty. <procedure>(make-random-rectangular-generator real-lower-bound real-upper-bound imaginary-lower-bound imag-upper-bound)</procedure> Returns a generator that generates inexact complex numbers uniformly. The procedure returns complex numbers in a rectangle whose real part is between {{real-lower-bound}} and {{real-upper-bound}} (both inclusive), and whose imaginary part is between {{imag-lower-bound}} and {{imag-upper-bound}} (both inclusive). It is an error if either of the specified intervals is empty. <procedure>(make-random-polar-generator [ origin ] magnitude-lower-bound magnitude-upper-bound [ angle-lower-bound angle-upper-bound ])</procedure> Returns a generator that generates inexact complex numbers uniformly. The procedure returns complex numbers in a sector of an annulus whose origin point is {{origin}}, whose magnitude is between {{magnitude-lower-bound}} and {{magnitude-upper-bound}} (both inclusive), and whose angle is between {{angle-lower-bound}} and {{angle-upper-bound}} (both inclusive). It is an error if either of the specified intervals is empty. The default value of origin is {{0+0i}}, the default value of {{angle-lower-bound}} is 0, and the default value of {{angle-upper-bound}} is {{2π}}. If all three are defaulted, the resulting shape is a disk centered on the origin. <procedure>(make-random-boolean-generator)</procedure> Generates boolean values (#f and #t) with equal probability. Chicken note: This is implemented using {{make-random-bernoullis}} from [[srfi-27]]. <procedure>(make-random-char-generator string)</procedure> Returns a generator that generates characters in {{string}} uniformly. Note that the characters in {{string}} need not be distinct, which allows simple weighting. It is an error if {{string}} is empty. <procedure>(make-random-string-generator k string)</procedure> Returns a generator that generates random strings whose characters are in {{string}}. Note that the characters in {{string}} need not be distinct, which allows simple weighting. The length of the strings is uniformly distributed between 0 (inclusive) and the length of {{string}} (exclusive). It is an error if {{string}} is empty. == Nonuniform distributions <procedure>(make-bernoulli-generator p)</procedure> Returns a generator that yields 1 with probability {{p}} and 0 with probability {{1 - p}}. Chicken note: This is implemented in terms of {{make-random-bernoullis}} from [[srfi-27]], except that {{make-random-bernoullis}} returns booleans, not integers. <procedure>(make-binomial-generator n p)</procedure> Returns a binomial random variate generator, which conceptually is the sum of n Bernoulli-p random variables. Chicken note: This is implemented in terms of {{make-random-binomials}} from [[srfi-27]]. <procedure>(make-categorical-generator weight-vec)</procedure> Returns a generator that yields an exact integer n between 0 (inclusive) and the length of {{weight-vec}} (inclusive) with probability equal to the {{n}}th element of {{weight-vec}} divided by the sum of its elements. It is an error if any element of {{weight-vec}} is negative or their sum is zero. <procedure>(make-normal-generator [ mean [ deviation ] ])</procedure> Returns a generator that yields real numbers from a normal distribution with the specified mean and deviation. The default value of mean is 0.0 and deviation is 1.0. Chicken note: This is implemented in terms of {{make-random-normals}} from [[srfi-27]]. <procedure>(make-exponential-generator mean)</procedure> Returns a generator that yields real numbers from an exponential distribution with the specified mean. Chicken note: Unlike {{make-random-exponentials}} from [[srfi-27]], this procedure does not limit {{mean}} to be less than or equal to 1. <procedure>(make-geometric-generator p)</procedure> Returns a generator that yields integers from the geometric distribution with success probability {{p}} {{(0 <= p <= 1)}}. The mean is {{1/p}} and variance is {{(1-p)/p^2}}. <procedure>(make-poisson-generator L)</procedure> Returns a generator that yields integers from the Poisson distribution with mean {{L}}, variance {{L}}. Chicken note: This is implemented in terms of {{make-random-poissons}} from [[srfi-27]]. <procedure>(make-zipf-generator N [ s [ q ] ])</procedure> Returns a generator that yields exact integers {{k}} from the generalized Zipf distribution {{1/(k+q^s)}} such that {{1 ≤ k ≤ N}}). The default value of {{s}} is 1.0 and the default value of {{q}} is 0.0. Parameters outside the following ranges are likely to result in overflows or loss of precision: {{-10 < s < 100}}, {{-0.5 < q < 2^8}}, and {{1 ≤ N}}. The following three procedures generate points of real k-dimensional Euclidean space. These points are modeled as Scheme vectors of real numbers of length k. <procedure>(make-sphere-generator n)</procedure> Returns a generator that generates points in real {{(n + 1)}}-dimensional Euclidean space that are randomly, independently distributed on the surface of an {{n}}-sphere. That is, the vectors are of unit length. <procedure>(make-ellipsoid-generator axes)</procedure> Returns a generator that generates points in real {{(n + 1)}}-dimensional Euclidean space that are randomly, independently distributed on the surface of an {{n}}-ellipsoid. The ellipsoid is specified by the axes argument, which must be a vector of real numbers giving the lengths of the axes. Given axes = {{(a, b, ...)}}, then the generated vectors {{v=(x, y, ...)}} obey {{1 = x2/a2 + y2/b2 + ... .}} <procedure>(make-ball-generator dimensions)</procedure> Returns a generator that generates points in real {{n}}-dimensional Euclidean space corresponding to the inside of an {{n}}-ball. The dimensions argument can be either a vector of {{n}} real numbers, in which case they are taken as the axes of an ellipsoid, or it can be an integer, in which case it's treated as the dimension {{n}}, (i.e. the generated vectors are inside a ball of radius 1.) === Generator Operations <procedure>(gsampling generator ...)</procedure> Takes the generators and returns a new generator. Every time the resulting generator is called, it picks one of the input generators with equal probability, then calls it to get a value. When all the generators are exhausted or no generators are specified, the new generator returns an end-of-file object. == Future Directions Currently the generators use Scheme's generic math procedures. Restricting everything to floats might make things faster. == Examples In the following examples, we use the {{generator->list}} procedure (from [[srfi-158]]) to show some concrete data from the generators. <enscript highlight="scheme"> (import (srfi 194) (srfi 158)) </enscript> === Generate a list of integers <enscript highlight="scheme"> ;; A die roller (define die (make-random-integer-generator 1 7)) ;; Roll the die 10 times (generator->list die 10) ; ⇒ (6 6 2 4 2 5 5 1 2 2) </enscript> === Generate signed 8 bit integers <enscript highlight="scheme"> (generator->list (make-random-s8-generator) 10) ;⇒ (20 -101 50 -99 -111 -28 -19 -61 39 110) </enscript> === Generate random reals <enscript highlight="scheme"> (define uniform-100 (make-random-real-generator 0 100)) (generator->list uniform-100 3) ;⇒ (81.67965004942268 81.84927577572596 53.02443813660833) (define generate-from-0-below-1 (gfilter (lambda (r) (not (= r 1.0))) (make-random-real-generator 0.0 1.0))) (generator->list generate-from-0-below-1 10) ; -> (0.474825107670301 0.822675192755749 0.0136297582264499 0.675879765670512 0.835390610797621 0.751728161787488 0.399774461321786 0.210700704442744 0.603465786092189 0.164001777794298) </enscript> === Generate random booleans <enscript highlight="scheme"> (generator->list (make-random-boolean-generator) 10) ;⇒ (#f #f #t #f #f #t #f #f #f #f) </enscript> === Generate random characters from a string <enscript highlight="scheme"> (define alphanumerics "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789") (define alphanumeric-chars (make-random-char-generator alphanumerics)) (generator->list alphanumeric-chars 10) ;⇒ (#\f #\m #\3 #\S #\z #\m #\x #\S #\l #\y) </enscript> === Draw numbers from the normal distribution <enscript highlight="scheme"> (import (srfi 1)) (define norm (make-normal-generator 1 2)) (define samples (generator->list norm 1000)) (/ (fold + 0 samples) (length samples)) ; -> 0.925 </enscript> == License 2020 Arvydas Silanskas, Bradley Lucier, Linas Vepštas, John Cowan 2024 Peter McGoron 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. == Version History * 1.0.0: Initial release
Description of your changes:
I would like to authenticate
Authentication
Username:
Password:
Spam control
What do you get when you multiply 4 by 9?