001/* 002 * Licensed to the Apache Software Foundation (ASF) under one or more 003 * contributor license agreements. See the NOTICE file distributed with 004 * this work for additional information regarding copyright ownership. 005 * The ASF licenses this file to You under the Apache License, Version 2.0 006 * (the "License"); you may not use this file except in compliance with 007 * the License. You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 */ 017package org.apache.commons.rng.simple; 018 019import org.apache.commons.rng.UniformRandomProvider; 020import org.apache.commons.rng.RestorableUniformRandomProvider; 021import org.apache.commons.rng.simple.internal.ProviderBuilder; 022import org.apache.commons.rng.simple.internal.SeedFactory; 023 024/** 025 * This class provides the API for creating generators of random numbers. 026 * 027 * <p>Usage examples:</p> 028 * <pre><code> 029 * UniformRandomProvider rng = RandomSource.create(RandomSource.MT); 030 * </code></pre> 031 * or 032 * <pre><code> 033 * final int[] seed = new int[] { 196, 9, 0, 226 }; 034 * UniformRandomProvider rng = RandomSource.create(RandomSource.MT, seed); 035 * </code></pre> 036 * or 037 * <pre><code> 038 * final int[] seed = RandomSource.createIntArray(256); 039 * UniformRandomProvider rng = RandomSource.create(RandomSource.MT, seed); 040 * </code></pre> 041 * where the first argument to method {@code create} is the identifier 042 * of the generator's concrete implementation, and the second the is the 043 * (optional) seed. 044 * 045 * <p> 046 * In the first form, a random seed will be {@link SeedFactory generated 047 * automatically}; in the second form, a fixed seed is used; a random seed 048 * is explicitly generated in the third form. 049 * </p> 050 * 051 * <p> 052 * Seeding is the procedure by which a value (or set of values) is 053 * used to <i>initialize</i> a generator instance. 054 * The requirement that a given seed will always result in the same 055 * internal state allows to create different instances of a generator 056 * that will produce the same sequence of pseudo-random numbers. 057 * </p> 058 * 059 * <p> 060 * The type of data used as a seed depends on the concrete implementation 061 * as some types may not provide enough information to fully initialize 062 * the generator's internal state. 063 * <br> 064 * The reference algorithm's seeding procedure (if provided) operates 065 * on a value of a (single) <i>native</i> type: 066 * Each concrete implementation's constructor creates an instance using 067 * the native type whose information contents is used to set the 068 * internal state. 069 * <br> 070 * When the seed value passed by the caller is of the native type, it is 071 * expected that the sequences produced will be identical to those 072 * produced by other implementations of the same reference algorithm. 073 * <br> 074 * However, when the seed value passed by the caller is not of the native 075 * type, a transformation is performed by this library and the resulting 076 * native type value will <i>not</i> contain more information than the 077 * original seed value. 078 * If the algorithm's native type is "simpler" than the type passed by 079 * the caller, then some (unused) information will even be lost. 080 * <br> 081 * The transformation from non-native to native seed type is arbitrary, 082 * as long as it does not reduce the amount of information required by 083 * the algorithm to initialize its state. 084 * The consequence of the transformation is that sequences produced 085 * by this library may <i>not</i> be the same as the sequences produced 086 * by other implementations of the same algorithm! 087 * </p> 088 * 089 * <p> 090 * For each algorithm, the Javadoc mentions the "ideal" size of the seed, 091 * meaning the number of {@code int} or {@code long} values that is neither 092 * too large (i.e. some of the seed is useless) or too small (i.e. an 093 * internal procedure will fill the state with redundant information 094 * computed from the given seed). 095 * </p> 096 * 097 * <p> 098 * Note that some algorithms are inherently sensitive to having too low 099 * diversity in their initial state. 100 * For example, it is often a bad idea to use a seed that is mostly 101 * composed of zeroes, or of repeated values. 102 * </p> 103 * 104 * <p> 105 * This class provides methods to generate random seeds (single values 106 * or arrays of values, of {@code int} or {@code long} types) that can 107 * be passed to the {@link RandomSource#create(RandomSource,Object,Object[]) 108 * generators factory method}. 109 * </p> 110 * <p> 111 * Although the seed-generating methods defined in this class will likely 112 * return different values each time they are called, there is no guarantee: 113 * </p> 114 * <ul> 115 * <li> 116 * In any sub-sequence, it is <a href="https://en.wikipedia.org/wiki/Birthday_problem"> 117 * expected</a> that the same numbers can occur, with a probability getting 118 * higher as the range of allowed values is smaller and the sequence becomes 119 * longer. 120 * </li> 121 * <li> 122 * It possible that the resulting "seed" will not be <i>good</i> (i.e. 123 * it will not generate a sufficiently uniformly random sequence for the 124 * intended purpose), even if the generator is good! 125 * The only way to ensure that the selected seed will make the generator 126 * produce a good sequence is to submit that sequence to a series of 127 * stringent tests, as provided by tools such as 128 * <a href="http://www.phy.duke.edu/~rgb/General/dieharder.php">dieharder</a> 129 * or <a href="http://simul.iro.umontreal.ca/testu01/tu01.html">TestU01</a>. 130 * </li> 131 * </ul> 132 * 133 * <p> 134 * The current implementations have no provision for producing non-overlapping 135 * sequences. 136 * For parallel applications, a possible workaround is that each thread uses 137 * a generator of a different type (see {@link #TWO_CMRES_SELECT}). 138 * </p> 139 * 140 * <p> 141 * <b>Note:</b> 142 * Seeding is not equivalent to restoring the internal state of an 143 * <i>already initialized</i> generator. 144 * Indeed, generators can have a state that is more complex than the 145 * seed, and seeding is thus a transformation (from seed to state). 146 * Implementations do not provide the inverse transformation (from 147 * state to seed), hence it is not generally possible to know the seed 148 * that would initialize a new generator instance to the current state 149 * of another instance. 150 * Reseeding is also inefficient if the purpose is to continue the 151 * same sequence where another instance left off, as it would require 152 * to "replay" all the calls performed by that other instance (and it 153 * would require to know the number of calls to the primary source of 154 * randomness, which is also not usually accessible). 155 * </p> 156 * 157 * @since 1.0 158 */ 159public enum RandomSource { 160 /** 161 * Source of randomness is {@link org.apache.commons.rng.core.source32.JDKRandom}. 162 * <ul> 163 * <li>Native seed type: {@code Long}.</li> 164 * </ul> 165 */ 166 JDK(ProviderBuilder.RandomSourceInternal.JDK), 167 /** 168 * Source of randomness is {@link org.apache.commons.rng.core.source32.Well512a}. 169 * <ul> 170 * <li>Native seed type: {@code int[]}.</li> 171 * <li>Native seed size: 16.</li> 172 * </ul> 173 */ 174 WELL_512_A(ProviderBuilder.RandomSourceInternal.WELL_512_A), 175 /** 176 * Source of randomness is {@link org.apache.commons.rng.core.source32.Well1024a}. 177 * <ul> 178 * <li>Native seed type: {@code int[]}.</li> 179 * <li>Native seed size: 32.</li> 180 * </ul> 181 */ 182 WELL_1024_A(ProviderBuilder.RandomSourceInternal.WELL_1024_A), 183 /** 184 * Source of randomness is {@link org.apache.commons.rng.core.source32.Well19937a}. 185 * <ul> 186 * <li>Native seed type: {@code int[]}.</li> 187 * <li>Native seed size: 624.</li> 188 * </ul> 189 */ 190 WELL_19937_A(ProviderBuilder.RandomSourceInternal.WELL_19937_A), 191 /** 192 * Source of randomness is {@link org.apache.commons.rng.core.source32.Well19937c}. 193 * <ul> 194 * <li>Native seed type: {@code int[]}.</li> 195 * <li>Native seed size: 624.</li> 196 * </ul> 197 */ 198 WELL_19937_C(ProviderBuilder.RandomSourceInternal.WELL_19937_C), 199 /** 200 * Source of randomness is {@link org.apache.commons.rng.core.source32.Well44497a}. 201 * <ul> 202 * <li>Native seed type: {@code int[]}.</li> 203 * <li>Native seed size: 1391.</li> 204 * </ul> 205 */ 206 WELL_44497_A(ProviderBuilder.RandomSourceInternal.WELL_44497_A), 207 /** 208 * Source of randomness is {@link org.apache.commons.rng.core.source32.Well44497b}. 209 * <ul> 210 * <li>Native seed type: {@code int[]}.</li> 211 * <li>Native seed size: 1391.</li> 212 * </ul> 213 */ 214 WELL_44497_B(ProviderBuilder.RandomSourceInternal.WELL_44497_B), 215 /** 216 * Source of randomness is {@link org.apache.commons.rng.core.source32.MersenneTwister}. 217 * <ul> 218 * <li>Native seed type: {@code int[]}.</li> 219 * <li>Native seed size: 624.</li> 220 * </ul> 221 */ 222 MT(ProviderBuilder.RandomSourceInternal.MT), 223 /** 224 * Source of randomness is {@link org.apache.commons.rng.core.source32.ISAACRandom}. 225 * <ul> 226 * <li>Native seed type: {@code int[]}.</li> 227 * <li>Native seed size: 256.</li> 228 * </ul> 229 */ 230 ISAAC(ProviderBuilder.RandomSourceInternal.ISAAC), 231 /** 232 * Source of randomness is {@link org.apache.commons.rng.core.source64.SplitMix64}. 233 * <ul> 234 * <li>Native seed type: {@code Long}.</li> 235 * </ul> 236 */ 237 SPLIT_MIX_64(ProviderBuilder.RandomSourceInternal.SPLIT_MIX_64), 238 /** 239 * Source of randomness is {@link org.apache.commons.rng.core.source64.XorShift1024Star}. 240 * <ul> 241 * <li>Native seed type: {@code long[]}.</li> 242 * <li>Native seed size: 16.</li> 243 * </ul> 244 * 245 * @deprecated Since 1.3, where it is recommended to use {@code XOR_SHIFT_1024_S_PHI} 246 * instead due to its slightly better (more uniform) output. {@code XOR_SHIFT_1024_S} 247 * is still quite usable but both are variants of the same algorithm and maintain their 248 * internal state identically. Their outputs are correlated and the two should not be 249 * used together when independent sequences are assumed. 250 */ 251 @Deprecated 252 XOR_SHIFT_1024_S(ProviderBuilder.RandomSourceInternal.XOR_SHIFT_1024_S), 253 /** 254 * Source of randomness is {@link org.apache.commons.rng.core.source64.TwoCmres}. 255 * This generator is equivalent to {@link #TWO_CMRES_SELECT} with the choice of the 256 * pair {@code (0, 1)} for the two subcycle generators. 257 * <ul> 258 * <li>Native seed type: {@code Integer}.</li> 259 * </ul> 260 */ 261 TWO_CMRES(ProviderBuilder.RandomSourceInternal.TWO_CMRES), 262 /** 263 * Source of randomness is {@link org.apache.commons.rng.core.source64.TwoCmres}, 264 * with explicit selection of the two subcycle generators. 265 * The selection of the subcycle generator is by passing its index in the internal 266 * table, a value between 0 (included) and 13 (included). 267 * The two indices must be different. 268 * Different choices of an ordered pair of indices create independent generators. 269 * <ul> 270 * <li>Native seed type: {@code Integer}.</li> 271 * </ul> 272 */ 273 TWO_CMRES_SELECT(ProviderBuilder.RandomSourceInternal.TWO_CMRES_SELECT), 274 /** 275 * Source of randomness is {@link org.apache.commons.rng.core.source64.MersenneTwister64}. 276 * <ul> 277 * <li>Native seed type: {@code long[]}.</li> 278 * <li>Native seed size: 312.</li> 279 * </ul> 280 */ 281 MT_64(ProviderBuilder.RandomSourceInternal.MT_64), 282 /** 283 * Source of randomness is {@link org.apache.commons.rng.core.source32.MultiplyWithCarry256}. 284 * <ul> 285 * <li>Native seed type: {@code int[]}.</li> 286 * <li>Native seed size: 257.</li> 287 * </ul> 288 */ 289 MWC_256(ProviderBuilder.RandomSourceInternal.MWC_256), 290 /** 291 * Source of randomness is {@link org.apache.commons.rng.core.source32.KISSRandom}. 292 * <ul> 293 * <li>Native seed type: {@code int[]}.</li> 294 * <li>Native seed size: 4.</li> 295 * </ul> 296 */ 297 KISS(ProviderBuilder.RandomSourceInternal.KISS), 298 /** 299 * Source of randomness is {@link org.apache.commons.rng.core.source64.XorShift1024StarPhi}. 300 * <ul> 301 * <li>Native seed type: {@code long[]}.</li> 302 * <li>Native seed size: 16.</li> 303 * </ul> 304 * @since 1.3 305 */ 306 XOR_SHIFT_1024_S_PHI(ProviderBuilder.RandomSourceInternal.XOR_SHIFT_1024_S_PHI), 307 /** 308 * Source of randomness is {@link org.apache.commons.rng.core.source32.XoRoShiRo64Star}. 309 * <ul> 310 * <li>Native seed type: {@code int[]}.</li> 311 * <li>Native seed size: 2.</li> 312 * </ul> 313 * @since 1.3 314 */ 315 XO_RO_SHI_RO_64_S(ProviderBuilder.RandomSourceInternal.XO_RO_SHI_RO_64_S), 316 /** 317 * Source of randomness is {@link org.apache.commons.rng.core.source32.XoRoShiRo64StarStar}. 318 * <ul> 319 * <li>Native seed type: {@code int[]}.</li> 320 * <li>Native seed size: 2.</li> 321 * </ul> 322 * @since 1.3 323 */ 324 XO_RO_SHI_RO_64_SS(ProviderBuilder.RandomSourceInternal.XO_RO_SHI_RO_64_SS), 325 /** 326 * Source of randomness is {@link org.apache.commons.rng.core.source32.XoShiRo128Plus}. 327 * <ul> 328 * <li>Native seed type: {@code int[]}.</li> 329 * <li>Native seed size: 4.</li> 330 * </ul> 331 * @since 1.3 332 */ 333 XO_SHI_RO_128_PLUS(ProviderBuilder.RandomSourceInternal.XO_SHI_RO_128_PLUS), 334 /** 335 * Source of randomness is {@link org.apache.commons.rng.core.source32.XoShiRo128StarStar}. 336 * <ul> 337 * <li>Native seed type: {@code int[]}.</li> 338 * <li>Native seed size: 4.</li> 339 * </ul> 340 * @since 1.3 341 */ 342 XO_SHI_RO_128_SS(ProviderBuilder.RandomSourceInternal.XO_SHI_RO_128_SS), 343 /** 344 * Source of randomness is {@link org.apache.commons.rng.core.source64.XoRoShiRo128Plus}. 345 * <ul> 346 * <li>Native seed type: {@code long[]}.</li> 347 * <li>Native seed size: 2.</li> 348 * </ul> 349 * @since 1.3 350 */ 351 XO_RO_SHI_RO_128_PLUS(ProviderBuilder.RandomSourceInternal.XO_RO_SHI_RO_128_PLUS), 352 /** 353 * Source of randomness is {@link org.apache.commons.rng.core.source64.XoRoShiRo128StarStar}. 354 * <ul> 355 * <li>Native seed type: {@code long[]}.</li> 356 * <li>Native seed size: 2.</li> 357 * </ul> 358 * @since 1.3 359 */ 360 XO_RO_SHI_RO_128_SS(ProviderBuilder.RandomSourceInternal.XO_RO_SHI_RO_128_SS), 361 /** 362 * Source of randomness is {@link org.apache.commons.rng.core.source64.XoShiRo256Plus}. 363 * <ul> 364 * <li>Native seed type: {@code long[]}.</li> 365 * <li>Native seed size: 4.</li> 366 * </ul> 367 * @since 1.3 368 */ 369 XO_SHI_RO_256_PLUS(ProviderBuilder.RandomSourceInternal.XO_SHI_RO_256_PLUS), 370 /** 371 * Source of randomness is {@link org.apache.commons.rng.core.source64.XoShiRo256StarStar}. 372 * <ul> 373 * <li>Native seed type: {@code long[]}.</li> 374 * <li>Native seed size: 4.</li> 375 * </ul> 376 * @since 1.3 377 */ 378 XO_SHI_RO_256_SS(ProviderBuilder.RandomSourceInternal.XO_SHI_RO_256_SS), 379 /** 380 * Source of randomness is {@link org.apache.commons.rng.core.source64.XoShiRo512Plus}. 381 * <ul> 382 * <li>Native seed type: {@code long[]}.</li> 383 * <li>Native seed size: 8.</li> 384 * </ul> 385 * @since 1.3 386 */ 387 XO_SHI_RO_512_PLUS(ProviderBuilder.RandomSourceInternal.XO_SHI_RO_512_PLUS), 388 /** 389 * Source of randomness is {@link org.apache.commons.rng.core.source64.XoShiRo512StarStar}. 390 * <ul> 391 * <li>Native seed type: {@code long[]}.</li> 392 * <li>Native seed size: 8.</li> 393 * </ul> 394 * @since 1.3 395 */ 396 XO_SHI_RO_512_SS(ProviderBuilder.RandomSourceInternal.XO_SHI_RO_512_SS), 397 /** 398 * Source of randomness is {@link org.apache.commons.rng.core.source32.PcgXshRr32}. 399 * <ul> 400 * <li>Native seed type: {@code long[]}.</li> 401 * <li>Native seed size: 2.</li> 402 * </ul> 403 * @since 1.3 404 */ 405 PCG_XSH_RR_32(ProviderBuilder.RandomSourceInternal.PCG_XSH_RR_32), 406 /** 407 * Source of randomness is {@link org.apache.commons.rng.core.source32.PcgXshRs32}. 408 * <ul> 409 * <li>Native seed type: {@code long[]}.</li> 410 * <li>Native seed size: 2.</li> 411 * </ul> 412 * @since 1.3 413 */ 414 PCG_XSH_RS_32(ProviderBuilder.RandomSourceInternal.PCG_XSH_RS_32), 415 /** 416 * Source of randomness is {@link org.apache.commons.rng.core.source64.PcgRxsMXs64}. 417 * <ul> 418 * <li>Native seed type: {@code long[]}.</li> 419 * <li>Native seed size: 2.</li> 420 * </ul> 421 * @since 1.3 422 */ 423 PCG_RXS_M_XS_64(ProviderBuilder.RandomSourceInternal.PCG_RXS_M_XS_64), 424 /** 425 * Source of randomness is {@link org.apache.commons.rng.core.source32.PcgMcgXshRr32}. 426 * <ul> 427 * <li>Native seed type: {@code Long}.</li> 428 * </ul> 429 * @since 1.3 430 */ 431 PCG_MCG_XSH_RR_32(ProviderBuilder.RandomSourceInternal.PCG_MCG_XSH_RR_32), 432 /** 433 * Source of randomness is {@link org.apache.commons.rng.core.source32.PcgMcgXshRs32}. 434 * <ul> 435 * <li>Native seed type: {@code Long}.</li> 436 * </ul> 437 * @since 1.3 438 */ 439 PCG_MCG_XSH_RS_32(ProviderBuilder.RandomSourceInternal.PCG_MCG_XSH_RS_32), 440 /** 441 * Source of randomness is {@link org.apache.commons.rng.core.source32.MiddleSquareWeylSequence}. 442 * <ul> 443 * <li>Native seed type: {@code long[]}.</li> 444 * <li>Native seed size: 3.</li> 445 * </ul> 446 * @since 1.3 447 */ 448 MSWS(ProviderBuilder.RandomSourceInternal.MSWS), 449 /** 450 * Source of randomness is {@link org.apache.commons.rng.core.source32.DotyHumphreySmallFastCounting32}. 451 * <ul> 452 * <li>Native seed type: {@code int[]}.</li> 453 * <li>Native seed size: 3.</li> 454 * </ul> 455 * @since 1.3 456 */ 457 SFC_32(ProviderBuilder.RandomSourceInternal.SFC_32), 458 /** 459 * Source of randomness is {@link org.apache.commons.rng.core.source64.DotyHumphreySmallFastCounting64}. 460 * <ul> 461 * <li>Native seed type: {@code long[]}.</li> 462 * <li>Native seed size: 3.</li> 463 * </ul> 464 * @since 1.3 465 */ 466 SFC_64(ProviderBuilder.RandomSourceInternal.SFC_64), 467 /** 468 * Source of randomness is {@link org.apache.commons.rng.core.source32.JenkinsSmallFast32}. 469 * <ul> 470 * <li>Native seed type: {@code Integer}.</li> 471 * </ul> 472 * @since 1.3 473 */ 474 JSF_32(ProviderBuilder.RandomSourceInternal.JSF_32), 475 /** 476 * Source of randomness is {@link org.apache.commons.rng.core.source64.JenkinsSmallFast64}. 477 * <ul> 478 * <li>Native seed type: {@code Long}.</li> 479 * </ul> 480 * @since 1.3 481 */ 482 JSF_64(ProviderBuilder.RandomSourceInternal.JSF_64), 483 /** 484 * Source of randomness is {@link org.apache.commons.rng.core.source32.XoShiRo128PlusPlus}. 485 * <ul> 486 * <li>Native seed type: {@code int[]}.</li> 487 * <li>Native seed size: 4.</li> 488 * </ul> 489 * @since 1.3 490 */ 491 XO_SHI_RO_128_PP(ProviderBuilder.RandomSourceInternal.XO_SHI_RO_128_PP), 492 /** 493 * Source of randomness is {@link org.apache.commons.rng.core.source64.XoRoShiRo128PlusPlus}. 494 * <ul> 495 * <li>Native seed type: {@code long[]}.</li> 496 * <li>Native seed size: 2.</li> 497 * </ul> 498 * @since 1.3 499 */ 500 XO_RO_SHI_RO_128_PP(ProviderBuilder.RandomSourceInternal.XO_RO_SHI_RO_128_PP), 501 /** 502 * Source of randomness is {@link org.apache.commons.rng.core.source64.XoShiRo256PlusPlus}. 503 * <ul> 504 * <li>Native seed type: {@code long[]}.</li> 505 * <li>Native seed size: 4.</li> 506 * </ul> 507 * @since 1.3 508 */ 509 XO_SHI_RO_256_PP(ProviderBuilder.RandomSourceInternal.XO_SHI_RO_256_PP), 510 /** 511 * Source of randomness is {@link org.apache.commons.rng.core.source64.XoShiRo512PlusPlus}. 512 * <ul> 513 * <li>Native seed type: {@code long[]}.</li> 514 * <li>Native seed size: 8.</li> 515 * </ul> 516 * @since 1.3 517 */ 518 XO_SHI_RO_512_PP(ProviderBuilder.RandomSourceInternal.XO_SHI_RO_512_PP), 519 /** 520 * Source of randomness is {@link org.apache.commons.rng.core.source64.XoRoShiRo1024PlusPlus}. 521 * <ul> 522 * <li>Native seed type: {@code long[]}.</li> 523 * <li>Native seed size: 16.</li> 524 * </ul> 525 * @since 1.3 526 */ 527 XO_RO_SHI_RO_1024_PP(ProviderBuilder.RandomSourceInternal.XO_RO_SHI_RO_1024_PP), 528 /** 529 * Source of randomness is {@link org.apache.commons.rng.core.source64.XoRoShiRo1024Star}. 530 * <ul> 531 * <li>Native seed type: {@code long[]}.</li> 532 * <li>Native seed size: 16.</li> 533 * </ul> 534 * @since 1.3 535 */ 536 XO_RO_SHI_RO_1024_S(ProviderBuilder.RandomSourceInternal.XO_RO_SHI_RO_1024_S), 537 /** 538 * Source of randomness is {@link org.apache.commons.rng.core.source64.XoRoShiRo1024StarStar}. 539 * <ul> 540 * <li>Native seed type: {@code long[]}.</li> 541 * <li>Native seed size: 16.</li> 542 * </ul> 543 * @since 1.3 544 */ 545 XO_RO_SHI_RO_1024_SS(ProviderBuilder.RandomSourceInternal.XO_RO_SHI_RO_1024_SS); 546 547 /** Internal identifier. */ 548 private final ProviderBuilder.RandomSourceInternal internalIdentifier; 549 550 /** 551 * @param id Internal identifier. 552 */ 553 RandomSource(ProviderBuilder.RandomSourceInternal id) { 554 internalIdentifier = id; 555 } 556 557 /** 558 * @return the internal identifier. 559 */ 560 ProviderBuilder.RandomSourceInternal getInternalIdentifier() { 561 return internalIdentifier; 562 } 563 564 /** 565 * Checks whether the type of given {@code seed} is the native type 566 * of the implementation. 567 * 568 * @param seed Seed value. 569 * @return {@code true} if the type of {@code seed} is the native 570 * type for this RNG source. 571 */ 572 public boolean isNativeSeed(Object seed) { 573 return internalIdentifier.isNativeSeed(seed); 574 } 575 576 /** 577 * Creates a seed suitable for the implementing class represented by this random source. 578 * 579 * <p>The seed will be created as if passing a {@code null} seed to the factory method 580 * {@link #create(RandomSource, Object, Object...)}. It will satisfy the seed size and any 581 * other seed requirements for the implementing class. The seed is converted from the native 582 * type to a byte representation.</p> 583 * 584 * <p>Usage example:</p> 585 * <pre><code> 586 * RandomSource source = ...; 587 * byte[] seed = source.createSeed(); 588 * UniformRandomProvider rng = RandomSource.create(source, seed); 589 * </code></pre> 590 * 591 * @return the seed 592 * @since 1.3 593 */ 594 public byte[] createSeed() { 595 return internalIdentifier.createSeedBytes(); 596 } 597 598 /** 599 * Creates a seed suitable for the implementing class represented by this random source 600 * using the supplied source of randomness. 601 * 602 * <p>The seed will satisfy the seed size and any other seed requirements for the 603 * implementing class.</p> 604 * 605 * <p>Usage example:</p> 606 * <pre><code> 607 * RandomSource source = ...; 608 * UniformRandomProvider seedRng = new JDKRandomWrapper(new SecureRandom()); 609 * byte[] seed = source.createSeed(seedRng); 610 * UniformRandomProvider rng = RandomSource.create(source, seed); 611 * </code></pre> 612 * 613 * @param rng Source of randomness. 614 * @return the seed 615 * @since 1.3 616 */ 617 public byte[] createSeed(UniformRandomProvider rng) { 618 return internalIdentifier.createSeedBytes(rng); 619 } 620 621 /** 622 * Checks whether the implementing class represented by this random source 623 * supports the {@link org.apache.commons.rng.JumpableUniformRandomProvider 624 * JumpableUniformRandomProvider} interface. If {@code true} the instance returned 625 * by {@link #create(RandomSource)} may be cast to the interface; otherwise a class 626 * cast exception will occur. 627 * 628 * <p>Usage example:</p> 629 * <pre><code> 630 * RandomSource source = ...; 631 * if (source.isJumpable()) { 632 * JumpableUniformRandomProvider rng = 633 * (JumpableUniformRandomProvider) RandomSource.create(source); 634 * } 635 * </code></pre> 636 * 637 * @return {@code true} if jumpable 638 * @since 1.3 639 */ 640 public boolean isJumpable() { 641 return isAssignableTo(org.apache.commons.rng.JumpableUniformRandomProvider.class); 642 } 643 644 /** 645 * Checks whether the implementing class represented by this random source 646 * supports the {@link org.apache.commons.rng.LongJumpableUniformRandomProvider 647 * LongJumpableUniformRandomProvider} interface. If {@code true} the instance returned 648 * by {@link #create(RandomSource)} may be cast to the interface; otherwise a class 649 * cast exception will occur. 650 * 651 * <p>Usage example:</p> 652 * <pre><code> 653 * RandomSource source = ...; 654 * if (source.isJumpable()) { 655 * LongJumpableUniformRandomProvider rng = 656 * (LongJumpableUniformRandomProvider) RandomSource.create(source); 657 * } 658 * </code></pre> 659 * 660 * @return {@code true} if long jumpable 661 * @since 1.3 662 */ 663 public boolean isLongJumpable() { 664 return isAssignableTo(org.apache.commons.rng.LongJumpableUniformRandomProvider.class); 665 } 666 667 /** 668 * Determines if the implementing class represented by this random source is either the same 669 * as, or is a subclass or subinterface of, the class or interface represented 670 * by the specified {@code Class} parameter. It returns true if so; otherwise it returns 671 * false. 672 * 673 * @param type the {@code Class} object to be checked 674 * @return the boolean value indicating whether the class of this random source 675 * can be assigned to objects of the specified type 676 */ 677 private boolean isAssignableTo(Class<?> type) { 678 return type.isAssignableFrom(internalIdentifier.getRng()); 679 } 680 681 /** 682 * Creates a random number generator with a random seed. 683 * 684 * <p>Usage example:</p> 685 * <pre><code> 686 * UniformRandomProvider rng = RandomSource.create(RandomSource.MT); 687 * </code></pre> 688 * <p>or, if a {@link RestorableUniformRandomProvider "save/restore"} functionality is needed,</p> 689 * <pre><code> 690 * RestorableUniformRandomProvider rng = RandomSource.create(RandomSource.MT); 691 * </code></pre> 692 * 693 * @param source RNG type. 694 * @return the RNG. 695 * 696 * @see #create(RandomSource,Object,Object[]) 697 */ 698 public static RestorableUniformRandomProvider create(RandomSource source) { 699 return ProviderBuilder.create(source.getInternalIdentifier()); 700 } 701 702 /** 703 * Creates a random number generator with the given {@code seed}. 704 * 705 * <p>Usage example:</p> 706 * <pre><code> 707 * UniformRandomProvider rng = RandomSource.create(RandomSource.TWO_CMRES_SELECT, 26219, 6, 9); 708 * </code></pre> 709 * 710 * <p>Valid types for the {@code seed} are:</p> 711 * <ul> 712 * <li>{@code Integer} (or {@code int})</li> 713 * <li>{@code Long} (or {@code long})</li> 714 * <li>{@code int[]}</li> 715 * <li>{@code long[]}</li> 716 * <li>{@code byte[]}</li> 717 * </ul> 718 * 719 * <p>Notes:</p> 720 * <ul> 721 * <li> 722 * When the seed type passed as argument is more complex (i.e. more 723 * bits can be independently chosen) than the generator's 724 * {@link #isNativeSeed(Object) native type}, the conversion of a 725 * set of different seeds will necessarily result in the same value 726 * of the native seed type. 727 * </li> 728 * <li> 729 * When the native seed type is an array, the same remark applies 730 * when the array contains more bits than the state of the generator. 731 * </li> 732 * <li> 733 * When the {@code seed} is {@code null}, a seed of the native type 734 * will be generated. If the native type is an array, the generated 735 * size is limited a maximum of 128. 736 * </li> 737 * </ul> 738 * 739 * @param source RNG type. 740 * @param seed Seed value. It can be {@code null} (in which case a 741 * random value will be used). 742 * @param data Additional arguments to the implementation's constructor. 743 * Please refer to the documentation of each specific implementation. 744 * @return the RNG. 745 * @throws UnsupportedOperationException if the type of the {@code seed} 746 * is invalid. 747 * @throws IllegalStateException if data is missing to initialize the 748 * generator implemented by the given {@code source}. 749 * 750 * @see #create(RandomSource) 751 */ 752 public static RestorableUniformRandomProvider create(RandomSource source, 753 Object seed, 754 Object... data) { 755 return ProviderBuilder.create(source.getInternalIdentifier(), seed, data); 756 } 757 758 /** 759 * Creates a number for use as a seed. 760 * 761 * @return a random number. 762 */ 763 public static int createInt() { 764 return SeedFactory.createInt(); 765 } 766 767 /** 768 * Creates a number for use as a seed. 769 * 770 * @return a random number. 771 */ 772 public static long createLong() { 773 return SeedFactory.createLong(); 774 } 775 776 /** 777 * Creates an array of numbers for use as a seed. 778 * 779 * @param n Size of the array to create. 780 * @return an array of {@code n} random numbers. 781 */ 782 public static int[] createIntArray(int n) { 783 return SeedFactory.createIntArray(n); 784 } 785 786 /** 787 * Creates an array of numbers for use as a seed. 788 * 789 * @param n Size of the array to create. 790 * @return an array of {@code n} random numbers. 791 */ 792 public static long[] createLongArray(int n) { 793 return SeedFactory.createLongArray(n); 794 } 795 796 /** 797 * Wraps the given {@code delegate} generator in a new instance that 798 * does not allow access to the "save/restore" functionality. 799 * 800 * @param delegate Generator to which calls will be delegated. 801 * @return a new instance whose state cannot be saved or restored. 802 */ 803 public static UniformRandomProvider unrestorable(final UniformRandomProvider delegate) { 804 return new UniformRandomProvider() { 805 /** {@inheritDoc} */ 806 @Override 807 public void nextBytes(byte[] bytes) { 808 delegate.nextBytes(bytes); 809 } 810 811 /** {@inheritDoc} */ 812 @Override 813 public void nextBytes(byte[] bytes, 814 int start, 815 int len) { 816 delegate.nextBytes(bytes, start, len); 817 } 818 819 /** {@inheritDoc} */ 820 @Override 821 public int nextInt() { 822 return delegate.nextInt(); 823 } 824 825 /** {@inheritDoc} */ 826 @Override 827 public int nextInt(int n) { 828 return delegate.nextInt(n); 829 } 830 831 /** {@inheritDoc} */ 832 @Override 833 public long nextLong() { 834 return delegate.nextLong(); 835 } 836 837 /** {@inheritDoc} */ 838 @Override 839 public long nextLong(long n) { 840 return delegate.nextLong(n); 841 } 842 843 /** {@inheritDoc} */ 844 @Override 845 public boolean nextBoolean() { 846 return delegate.nextBoolean(); 847 } 848 849 /** {@inheritDoc} */ 850 @Override 851 public float nextFloat() { 852 return delegate.nextFloat(); 853 } 854 855 /** {@inheritDoc} */ 856 @Override 857 public double nextDouble() { 858 return delegate.nextDouble(); 859 } 860 861 /** {@inheritDoc} */ 862 @Override 863 public String toString() { 864 return delegate.toString(); 865 } 866 }; 867 } 868}