mirror of
https://github.com/nim-lang/Nim.git
synced 2025-12-30 01:44:37 +00:00
62 lines
1.0 KiB
Nim
62 lines
1.0 KiB
Nim
discard """
|
|
output: '''
|
|
true
|
|
true
|
|
true
|
|
3
|
|
18.0
|
|
324.0
|
|
'''
|
|
"""
|
|
|
|
type RNG = object
|
|
|
|
proc random(rng: var RNG): float = 1.0
|
|
|
|
type
|
|
RandomVar[A] = concept x
|
|
var rng: RNG
|
|
rng.sample(x) is A
|
|
|
|
Constant[A] = object
|
|
value: A
|
|
|
|
Uniform = object
|
|
a, b: float
|
|
|
|
ClosureVar[A] = proc(rng: var RNG): A
|
|
|
|
proc sample[A](rng: var RNG, c: Constant[A]): A = c.value
|
|
|
|
proc sample(rng: var RNG, u: Uniform): float = u.a + (u.b - u.a) * rng.random()
|
|
|
|
proc sample[A](rng: var RNG, c: ClosureVar[A]): A = c(rng)
|
|
|
|
proc constant[A](a: A): Constant[A] = Constant[A](value: a)
|
|
|
|
proc uniform(a, b: float): Uniform = Uniform(a: a, b: b)
|
|
|
|
proc lift1[A, B](f: proc(a: A): B, r: RandomVar[A]): ClosureVar[B] =
|
|
proc inner(rng: var RNG): B = f(rng.sample(r))
|
|
|
|
return inner
|
|
|
|
when isMainModule:
|
|
proc sq(x: float): float = x * x
|
|
|
|
let
|
|
c = constant(3)
|
|
u = uniform(2, 18)
|
|
t = lift1(sq, u)
|
|
|
|
var rng: RNG
|
|
|
|
echo(c is RandomVar[int])
|
|
echo(u is RandomVar[float])
|
|
echo(t is RandomVar[float])
|
|
|
|
echo rng.sample(c)
|
|
echo rng.sample(u)
|
|
echo rng.sample(t)
|
|
|