2020-08-02 23:56:21 +03:00
|
|
|
-- Random data structures generator.
|
|
|
|
|
-- (C) Dmitry Boulytchev, JetBrains Research, St. Petersburg State University, 2020
|
|
|
|
|
--
|
|
|
|
|
-- This unit provides an implementation for random data structures generator
|
|
|
|
|
|
|
|
|
|
import Array;
|
|
|
|
|
|
|
|
|
|
-- Generates a random signed 31-bit integer
|
|
|
|
|
public fun randomInt () {
|
|
|
|
|
if random (2)
|
|
|
|
|
then random (1073741823)
|
|
|
|
|
else 0 - random (1073741823)
|
|
|
|
|
fi
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
-- Generates a printable ASCII string of given length
|
|
|
|
|
public fun randomString (len) {
|
2021-01-31 22:25:31 +03:00
|
|
|
var s = makeString (len);
|
2020-08-02 23:56:21 +03:00
|
|
|
|
2021-01-31 22:25:31 +03:00
|
|
|
for var i = 0;, i < len, i := i+1
|
2020-08-02 23:56:21 +03:00
|
|
|
do
|
|
|
|
|
s [i] := 32 + random (94) -- printable ASCII set
|
|
|
|
|
od;
|
|
|
|
|
|
|
|
|
|
s
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
-- Generates a random array of (deep) size n. f is element-generation
|
|
|
|
|
-- function which takes the size of the element
|
|
|
|
|
public fun randomArray (f, n) {
|
2020-08-22 20:11:41 +03:00
|
|
|
mapArray (f, split (n, random (n + 1)))
|
2020-08-02 23:56:21 +03:00
|
|
|
}
|
|
|
|
|
|
2020-08-22 20:11:41 +03:00
|
|
|
-- Splits a number n in a random sequence of k summands
|
|
|
|
|
public fun split (n, k) {
|
2021-01-31 22:25:31 +03:00
|
|
|
var a = makeArray (k),
|
2020-08-02 23:56:21 +03:00
|
|
|
m = n;
|
|
|
|
|
|
2021-01-31 22:25:31 +03:00
|
|
|
for var i = 0;, i < k, i := i + 1
|
2020-08-02 23:56:21 +03:00
|
|
|
do
|
|
|
|
|
if i == k - 1
|
|
|
|
|
then a[i] := m
|
|
|
|
|
else
|
|
|
|
|
a [i] := random (m - k + i + 1) + 1;
|
|
|
|
|
m := m - a [i]
|
|
|
|
|
fi
|
|
|
|
|
od;
|
|
|
|
|
|
|
|
|
|
a
|
|
|
|
|
}
|
2020-08-22 20:11:41 +03:00
|
|
|
|
|
|
|
|
-- Generates a (recursive) data structure of size n. nodeSpec is an array of pairs [n, fn] where
|
|
|
|
|
-- fn gets an array of values of length n and generates some node; leaf is a fucntion without
|
|
|
|
|
-- arguments which create a leaf.
|
|
|
|
|
public fun structure (n, nodeSpec, leaf) {
|
2021-01-31 22:25:31 +03:00
|
|
|
var k = nodeSpec.length;
|
2020-08-22 20:11:41 +03:00
|
|
|
|
|
|
|
|
fun rec (n) {
|
|
|
|
|
if n <= 1
|
|
|
|
|
then leaf ()
|
|
|
|
|
else
|
2021-01-31 22:25:31 +03:00
|
|
|
var ns = nodeSpec [random (k)];
|
2020-08-22 20:11:41 +03:00
|
|
|
|
|
|
|
|
ns [1] (mapArray (rec, split (n, ns [0])))
|
|
|
|
|
fi
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
rec (n)
|
|
|
|
|
}
|