110 lines
2.4 KiB
Gleam
110 lines
2.4 KiB
Gleam
import birl
|
|
import birl/duration.{Duration}
|
|
import gleam/int
|
|
import gleam/io
|
|
import gleam/list
|
|
import gleam/otp/task
|
|
import gleam/string
|
|
import query
|
|
import tree
|
|
|
|
pub fn main() {
|
|
kv_bench()
|
|
tree_bench()
|
|
}
|
|
|
|
fn kv_bench() {
|
|
let ts = birl.now()
|
|
let tree = tree.new() |> fill(0)
|
|
let ts2 = birl.now()
|
|
let Duration(ms) = birl.difference(ts2, ts)
|
|
{ "Set 1M key-value pairs in " <> string.inspect(ms / 10) <> " ms." }
|
|
|> io.debug
|
|
|
|
let tasks = tree |> setup_tasks()
|
|
let ts = birl.now()
|
|
tasks |> list.map(fn(task) { task |> task.await_forever() })
|
|
let ts2 = birl.now()
|
|
let Duration(ms) = birl.difference(ts2, ts)
|
|
{
|
|
"Read 1M key-value pairs using 10 actors in "
|
|
<> string.inspect(ms / 10)
|
|
<> " ms."
|
|
}
|
|
|> io.debug
|
|
}
|
|
|
|
fn fill(tree, i) {
|
|
case i {
|
|
1_000_000 -> tree
|
|
_ -> {
|
|
let assert Ok(tree) =
|
|
tree |> query.set([".", int.to_string(i)], tree.Int(i))
|
|
tree |> fill(i + 1)
|
|
}
|
|
}
|
|
}
|
|
|
|
fn get_100k(tree, i) {
|
|
case i {
|
|
100_000 -> Nil
|
|
_ -> {
|
|
let rint = int.random(1_000_000)
|
|
let assert Ok(_) =
|
|
tree |> query.get([".", rint |> int.to_string()], False)
|
|
get_100k(tree, i + 1)
|
|
}
|
|
}
|
|
}
|
|
|
|
fn setup_tasks(tree) {
|
|
list.range(0, 10)
|
|
|> list.map(fn(_) { task.async(fn() { tree |> get_100k(0) }) })
|
|
}
|
|
|
|
fn tree_bench() {
|
|
let paths = list.range(0, 1_000_000) |> list.map(fn(n) { n |> path })
|
|
let ts = birl.now()
|
|
let tree = tree.new() |> fill_tree(paths)
|
|
let ts2 = birl.now()
|
|
let Duration(ms) = birl.difference(ts2, ts)
|
|
{ "Set 1M nodes in " <> string.inspect(ms / 10) <> " ms." } |> io.debug
|
|
|
|
let tasks = tree |> setup_nodes_tasks(paths)
|
|
let ts = birl.now()
|
|
tasks |> list.map(fn(task) { task |> task.await_forever() })
|
|
let ts2 = birl.now()
|
|
let Duration(ms) = birl.difference(ts2, ts)
|
|
{ "Read 1M nodes using 10 actors in " <> string.inspect(ms / 10) <> " ms." }
|
|
|> io.debug
|
|
}
|
|
|
|
fn fill_tree(tree, paths) {
|
|
paths
|
|
|> list.fold(tree, fn(tree, path) {
|
|
let assert Ok(tree) = tree |> query.set(path, tree.String("foo"))
|
|
tree
|
|
})
|
|
}
|
|
|
|
fn setup_nodes_tasks(tree, paths) {
|
|
let paths = paths |> list.sized_chunk(100_000)
|
|
list.range(0, 10)
|
|
|> list.map2(paths, fn(_, path) {
|
|
task.async(fn() { tree |> get_nodes(path) })
|
|
})
|
|
}
|
|
|
|
fn get_nodes(tree, paths) {
|
|
paths
|
|
|> list.fold(tree, fn(tree, path) {
|
|
let _ = tree |> query.get(path, True)
|
|
tree
|
|
})
|
|
}
|
|
|
|
fn path(i: Int) {
|
|
{ i |> int.to_string() |> string.to_graphemes }
|
|
|> list.reverse()
|
|
}
|