♻️🍱 config, cli, vanth, vanth_derive, varo: Reformatted code and added editor configuration files

- Added `.zed/settings.json` to configure rust-analyzer with `leptosfmt`.
- Created `rustfmt.toml` with max width 120 and comment wrapping settings.
- Applied consistent formatting across all modified crates using rustfmt.
- Reorganized import statements and improved code style in multiple modules.
This commit is contained in:
Markus Scully 2025-08-07 12:49:33 +03:00
parent 87957bfbf8
commit 9e7979931c
Signed by: mascully
GPG key ID: 93CA5814B698101C
15 changed files with 141 additions and 161 deletions

11
.zed/settings.json Normal file
View file

@ -0,0 +1,11 @@
{
"lsp": {
"rust-analyzer": {
"initialization_options": {
"rustfmt": {
"overrideCommand": ["leptosfmt", "--stdin", "--rustfmt"]
}
}
}
}
}

View file

@ -44,4 +44,4 @@ pub fn execute(cli: Cli) {
}
},
}
}
}

View file

@ -122,13 +122,7 @@ impl<T: ?Sized> Hash for Id<T> {
impl<T: ?Sized> Debug for Id<T> {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
let (high, low) = self.to_u128_pair();
write!(
f,
"Id<{}>({:016x}{:016x})",
std::any::type_name::<T>(),
high,
low
)
write!(f, "Id<{}>({:016x}{:016x})", std::any::type_name::<T>(), high, low)
}
}
@ -146,7 +140,9 @@ pub struct ContentHash {
impl ContentHash {}
pub trait Entity {
fn entity_id() -> Id<dyn Entity> where Self: Sized;
fn entity_id() -> Id<dyn Entity>
where
Self: Sized;
}
pub trait Component: Send + Sync + 'static {

View file

@ -4,11 +4,11 @@ use std::fmt;
use digest::Update;
use serde::{
Serialize, Serializer,
ser::{
self, SerializeMap, SerializeSeq, SerializeStruct, SerializeStructVariant, SerializeTuple,
SerializeTupleStruct, SerializeTupleVariant,
},
Serialize, Serializer,
};
use crate::ContentHash;
@ -18,7 +18,9 @@ pub fn hash(value: &impl Serialize) -> ContentHash {
let mut serializer = HashingSerializer { digest: &mut digest };
// TODO: Don't unwrap.
serializer.serialize_value(value).unwrap();
ContentHash { hash: *serializer.digest.finalize().as_bytes() }
ContentHash {
hash: *serializer.digest.finalize().as_bytes(),
}
}
/// A serializer that hashes the data instead of serializing it.
@ -70,9 +72,7 @@ impl fmt::Display for Error {
/// Converts the `usize` sequence length to a fixed length type,
/// since we want the result to be portable.
fn try_into_sequence_length(len: usize) -> Result<u128, Error> {
u128::try_from(len)
.ok()
.ok_or(Error::SequenceLengthTooLarge)
u128::try_from(len).ok().ok_or(Error::SequenceLengthTooLarge)
}
// Implement `serialize_$ty` for int types
@ -189,14 +189,12 @@ impl<'a, T: Update> Serializer for HashingSerializer<'a, T> {
fn serialize_seq(self, len: Option<usize>) -> Result<Self::SerializeSeq, Self::Error> {
let len = len.ok_or(Error::UndefinedSequenceLength)?;
self.digest
.update(&try_into_sequence_length(len)?.to_be_bytes());
self.digest.update(&try_into_sequence_length(len)?.to_be_bytes());
Ok(self)
}
fn serialize_tuple(self, len: usize) -> Result<Self::SerializeTuple, Self::Error> {
self.digest
.update(&try_into_sequence_length(len)?.to_be_bytes());
self.digest.update(&try_into_sequence_length(len)?.to_be_bytes());
Ok(self)
}
@ -205,8 +203,7 @@ impl<'a, T: Update> Serializer for HashingSerializer<'a, T> {
_name: &'static str,
len: usize,
) -> Result<Self::SerializeTupleStruct, Self::Error> {
self.digest
.update(&try_into_sequence_length(len)?.to_be_bytes());
self.digest.update(&try_into_sequence_length(len)?.to_be_bytes());
Ok(self)
}
@ -218,25 +215,18 @@ impl<'a, T: Update> Serializer for HashingSerializer<'a, T> {
len: usize,
) -> Result<Self::SerializeTupleVariant, Self::Error> {
self.digest.update(&variant_index.to_be_bytes());
self.digest
.update(&try_into_sequence_length(len)?.to_be_bytes());
self.digest.update(&try_into_sequence_length(len)?.to_be_bytes());
Ok(self)
}
fn serialize_map(self, len: Option<usize>) -> Result<Self::SerializeMap, Self::Error> {
let len = len.ok_or(Error::UndefinedSequenceLength)?;
self.digest
.update(&try_into_sequence_length(len)?.to_be_bytes());
self.digest.update(&try_into_sequence_length(len)?.to_be_bytes());
Ok(self)
}
fn serialize_struct(
self,
_name: &'static str,
len: usize,
) -> Result<Self::SerializeStruct, Self::Error> {
self.digest
.update(&try_into_sequence_length(len)?.to_be_bytes());
fn serialize_struct(self, _name: &'static str, len: usize) -> Result<Self::SerializeStruct, Self::Error> {
self.digest.update(&try_into_sequence_length(len)?.to_be_bytes());
Ok(self)
}
@ -248,8 +238,7 @@ impl<'a, T: Update> Serializer for HashingSerializer<'a, T> {
len: usize,
) -> Result<Self::SerializeStructVariant, Self::Error> {
self.digest.update(&variant_index.to_be_bytes());
self.digest
.update(&try_into_sequence_length(len)?.to_be_bytes());
self.digest.update(&try_into_sequence_length(len)?.to_be_bytes());
Ok(self)
}
@ -267,9 +256,7 @@ impl<'a, T: Update> SerializeSeq for HashingSerializer<'a, T> {
type Error = Error;
fn serialize_element<V: ?Sized + Serialize>(&mut self, value: &V) -> Result<Self::Ok, Error> {
value.serialize(HashingSerializer {
digest: self.digest,
})?;
value.serialize(HashingSerializer { digest: self.digest })?;
Ok(())
}
@ -283,9 +270,7 @@ impl<'a, T: Update> SerializeTuple for HashingSerializer<'a, T> {
type Error = Error;
fn serialize_element<V: ?Sized + Serialize>(&mut self, value: &V) -> Result<Self::Ok, Error> {
value.serialize(HashingSerializer {
digest: self.digest,
})?;
value.serialize(HashingSerializer { digest: self.digest })?;
Ok(())
}
@ -299,9 +284,7 @@ impl<'a, T: Update> SerializeTupleStruct for HashingSerializer<'a, T> {
type Error = Error;
fn serialize_field<V: ?Sized + Serialize>(&mut self, value: &V) -> Result<Self::Ok, Error> {
value.serialize(HashingSerializer {
digest: self.digest,
})?;
value.serialize(HashingSerializer { digest: self.digest })?;
Ok(())
}
@ -315,9 +298,7 @@ impl<'a, T: Update> SerializeTupleVariant for HashingSerializer<'a, T> {
type Error = Error;
fn serialize_field<V: ?Sized + Serialize>(&mut self, value: &V) -> Result<Self::Ok, Error> {
value.serialize(HashingSerializer {
digest: self.digest,
})?;
value.serialize(HashingSerializer { digest: self.digest })?;
Ok(())
}
@ -331,16 +312,12 @@ impl<'a, T: Update> SerializeMap for HashingSerializer<'a, T> {
type Error = Error;
fn serialize_key<K: ?Sized + Serialize>(&mut self, key: &K) -> Result<Self::Ok, Error> {
key.serialize(HashingSerializer {
digest: self.digest,
})?;
key.serialize(HashingSerializer { digest: self.digest })?;
Ok(())
}
fn serialize_value<V: ?Sized + Serialize>(&mut self, value: &V) -> Result<Self::Ok, Error> {
value.serialize(HashingSerializer {
digest: self.digest,
})?;
value.serialize(HashingSerializer { digest: self.digest })?;
Ok(())
}
@ -353,14 +330,8 @@ impl<'a, T: Update> SerializeStruct for HashingSerializer<'a, T> {
type Ok = ();
type Error = Error;
fn serialize_field<V: ?Sized + Serialize>(
&mut self,
_key: &'static str,
value: &V,
) -> Result<Self::Ok, Error> {
value.serialize(HashingSerializer {
digest: self.digest,
})?;
fn serialize_field<V: ?Sized + Serialize>(&mut self, _key: &'static str, value: &V) -> Result<Self::Ok, Error> {
value.serialize(HashingSerializer { digest: self.digest })?;
Ok(())
}
@ -373,14 +344,8 @@ impl<'a, T: Update> SerializeStructVariant for HashingSerializer<'a, T> {
type Ok = ();
type Error = Error;
fn serialize_field<V: ?Sized + Serialize>(
&mut self,
_key: &'static str,
value: &V,
) -> Result<Self::Ok, Error> {
value.serialize(HashingSerializer {
digest: self.digest,
})?;
fn serialize_field<V: ?Sized + Serialize>(&mut self, _key: &'static str, value: &V) -> Result<Self::Ok, Error> {
value.serialize(HashingSerializer { digest: self.digest })?;
Ok(())
}

View file

@ -3,13 +3,13 @@ use std::marker::PhantomData;
/// Library crate for the `vanth` ECS-based database node.
use bevy_app::{App, Plugin};
use bevy_ecs::{prelude::*, query::QueryData};
use serde::{de::DeserializeOwned, Deserialize, Serialize};
use serde::{Deserialize, Serialize, de::DeserializeOwned};
use crate::entity::EntityId;
pub mod store;
pub mod entity;
pub mod hashing_serializer;
pub mod store;
pub use hashing_serializer::hash;
pub use vanth_derive::Vanth;
@ -38,17 +38,15 @@ impl Node {
// Query for no components returns one item per entity.
// self.app.world().entities().len()
}
// TODO
pub fn run() {
}
pub fn run() {}
pub fn save(entity_id: impl Into<EntityId>) -> Result<()> {
// TODO
Ok(())
}
// pub fn load(entity_id: impl Into<EntityId>) -> Result<Option<EntityContents>> {
// // TODO
// Ok(None)
@ -58,7 +56,7 @@ impl Node {
#[derive(Clone, Debug, Deserialize, Serialize)]
pub struct HashedValue {
content_hash: ContentHash,
inner: Value
inner: Value,
}
impl From<Value> for HashedValue {
@ -68,7 +66,7 @@ impl From<Value> for HashedValue {
inner: value,
}
}
}
}
#[derive(Clone, Debug, Deserialize, Serialize)]
pub struct Value {
@ -93,9 +91,9 @@ impl PartialEq for Ty {
}
}
impl <T: AsRef<str>> PartialEq<T> for Ty {
impl<T: AsRef<str>> PartialEq<T> for Ty {
fn eq(&self, other: &T) -> bool {
self.to_string() == *other.as_ref()
self.to_string() == *other.as_ref()
}
}
@ -104,9 +102,7 @@ pub trait Vanth {
}
// TODO: Impl for different tuple sizes
pub trait VanthTuple {
}
pub trait VanthTuple {}
// #[derive(Clone, Debug, Deserialize, Serialize)]
// pub struct EntityContents {
@ -134,30 +130,28 @@ pub struct ContentHash {
#[derive(Clone, Debug, Deserialize, Component, Serialize)]
pub struct Reference<T: Clone + Serialize> {
value: ReferenceValue,
_marker: PhantomData<T>
_marker: PhantomData<T>,
}
#[derive(Clone, Debug, Deserialize, Component, Serialize)]
pub enum ReferenceValue {
Absent,
Retrieving(ReferenceRetrievalTask),
Present(Vec<u8>)
Present(Vec<u8>),
}
impl <T: Clone + Serialize> Reference<T> {
impl<T: Clone + Serialize> Reference<T> {
pub async fn take() -> T {
todo!()
}
pub async fn get() -> Handle<T> {
todo!()
}
}
#[derive(Component, Clone, Debug, Deserialize, Serialize)]
pub struct ReferenceRetrievalTask {
}
pub struct ReferenceRetrievalTask {}
impl Future for ReferenceRetrievalTask {
type Output = Vec<u8>;
@ -168,19 +162,19 @@ impl Future for ReferenceRetrievalTask {
}
pub struct Handle<T> {
_marker: PhantomData<T>
_marker: PhantomData<T>,
}
// TODO:
// A trait is derivable for ECS components
// The components must have a content hash, not the entity. For efficiency and ergonomics. This means that a hash of each relevant component must be stored in the Vanth component of the entity, in a `HashMap` or something. The ID of the component used by Vanth should be a method on the derived trait.
// The components must have a content hash, not the entity. For efficiency and ergonomics. This means that a hash of
// each relevant component must be stored in the Vanth component of the entity, in a `HashMap` or something. The ID of
// the component used by Vanth should be a method on the derived trait.
pub struct VanthPlugin;
impl Plugin for VanthPlugin {
fn build(&self, app: &mut App) {
}
fn build(&self, app: &mut App) {}
}
// fn run_reference_tasks(tasks: Query<(&ReferenceGetTask<>)>) {
@ -188,6 +182,4 @@ impl Plugin for VanthPlugin {
// }
/// A world which Vanth entities live in. Lifetimes `'v` of [`Vanth<'v>`] types are tied to the lifetime of the `Root`.
pub struct Root {
}
pub struct Root {}

View file

@ -1,11 +1,11 @@
use std::{collections::HashMap, marker::PhantomData, path::PathBuf};
use rusqlite::{Connection, params, named_params};
use rusqlite::{Connection, named_params, params};
use bevy_ecs::prelude::*;
use serde::{de::DeserializeOwned, Deserialize, Serialize};
use serde::{Deserialize, Serialize, de::DeserializeOwned};
use crate::{hash, ComponentContents, ContentHash, Ty, Vanth};
use crate::{ComponentContents, ContentHash, Ty, Vanth, hash};
#[derive(Debug)]
pub struct Store {
@ -22,7 +22,7 @@ pub enum Error {
impl From<serde_json::Error> for Error {
fn from(err: serde_json::Error) -> Self {
Error::Serializiation(err.to_string())
Error::Serializiation(err.to_string())
}
}
@ -48,13 +48,15 @@ impl Store {
}
pub fn get_from_hash<T: Vanth + DeserializeOwned>(&mut self, content_hash: ContentHash) -> Result<Option<T>> {
let Some(raw) = self.get_raw_from_hash::<T>(content_hash)? else { return Ok(None) };
let Some(raw) = self.get_from_hash_raw::<T>(content_hash)? else {
return Ok(None);
};
let deserialized: T = serde_json::from_slice(&raw)?;
Ok(Some(deserialized))
Ok(Some(deserialized))
}
pub fn get_raw_from_hash<T: Vanth>(&mut self, content_hash: ContentHash) -> Result<Option<Vec<u8>>> {
pub fn get_from_hash_raw<T: Vanth>(&mut self, content_hash: ContentHash) -> Result<Option<Vec<u8>>> {
self.backend.get_from_hash(T::ty(), content_hash)
}
@ -144,9 +146,11 @@ impl Backend for Sqlite {
let table_name = Self::table_name(&ty);
let query = format!("SELECT content FROM \"{}\" WHERE content_hash = :hash", table_name);
match self.conn.query_row(&query, named_params! {":hash": content_hash.hash.as_slice()}, |row| {
row.get::<_, Vec<u8>>(0)
}) {
match self
.conn
.query_row(&query, named_params! {":hash": content_hash.hash.as_slice()}, |row| {
row.get::<_, Vec<u8>>(0)
}) {
Ok(content) => Ok(Some(content)),
Err(rusqlite::Error::QueryReturnedNoRows) => Ok(None),
Err(e) => Err(e.into()),
@ -181,7 +185,10 @@ impl Backend for Sqlite {
"INSERT OR REPLACE INTO \"{}\" (content_hash, content) VALUES (:hash, :content)",
table_name
);
self.conn.execute(&query, named_params! {":hash": content_hash.hash.as_slice(), ":content": content})?;
self.conn.execute(
&query,
named_params! {":hash": content_hash.hash.as_slice(), ":content": content},
)?;
Ok(())
}
@ -189,7 +196,8 @@ impl Backend for Sqlite {
self.ensure_table_exists(&ty)?;
let table_name = Self::table_name(&ty);
let query = format!("DELETE FROM \"{}\" WHERE content_hash = :hash", table_name);
self.conn.execute(&query, named_params! {":hash": content_hash.hash.as_slice()})?;
self.conn
.execute(&query, named_params! {":hash": content_hash.hash.as_slice()})?;
Ok(())
}
@ -209,28 +217,20 @@ pub struct Memory {
impl Memory {
pub fn new() -> Self {
Self {
tables: HashMap::new(),
}
Self { tables: HashMap::new() }
}
}
impl Backend for Memory {
fn get_from_hash(&mut self, ty: Ty, content_hash: ContentHash) -> Result<Option<Vec<u8>>> {
Ok(self.tables
.get(&ty)
.and_then(|table| table.get(&content_hash))
.cloned())
Ok(self.tables.get(&ty).and_then(|table| table.get(&content_hash)).cloned())
}
fn get_all_of_ty(&mut self, ty: Ty) -> Result<Vec<(ContentHash, Vec<u8>)>> {
Ok(self.tables
Ok(self
.tables
.get(&ty)
.map(|table| {
table.iter()
.map(|(k, v)| (*k, v.clone()))
.collect()
})
.map(|table| table.iter().map(|(k, v)| (*k, v.clone())).collect())
.unwrap_or_else(Vec::new))
}

View file

@ -1,12 +1,10 @@
use bevy_ecs::component::Component;
use serde::{de::DeserializeOwned, Deserialize, Serialize};
use serde::{Deserialize, Serialize, de::DeserializeOwned};
use vanth::Vanth;
// TODO: derive `Vanth`
#[derive(Debug, Deserialize, Component, Serialize)]
struct Foo {
}
struct Foo {}
#[test]
fn test_derive() {
@ -16,12 +14,12 @@ fn test_derive() {
field_b: String,
inner: T,
}
#[derive(Deserialize, Serialize, Vanth)]
struct Bar {
field_a: i32,
}
#[derive(Deserialize, Serialize, Vanth)]
struct Qux<T: Vanth, S: Vanth> {
field_a: i32,
@ -29,10 +27,13 @@ fn test_derive() {
inner: T,
inner_2: S,
}
let base = "integration::derive::";
assert_eq!(Bar::ty(), format!("{base}Bar"));
assert_eq!(Foo::<Bar>::ty(), format!("{base}Foo<{base}Bar>"));
assert_eq!(Qux::<Bar, Foo<Bar>>::ty(), format!("{base}Qux<{base}Bar,{base}Foo<{base}Bar>>"));
assert_eq!(
Qux::<Bar, Foo<Bar>>::ty(),
format!("{base}Qux<{base}Bar,{base}Foo<{base}Bar>>")
);
}

View file

@ -0,0 +1 @@

View file

@ -3,5 +3,5 @@ use vanth::{Component, Node, Reference};
mod derive;
mod fs;
mod store;
mod reference;
mod store;

View file

@ -1,4 +1,9 @@
use bevy_ecs::{component::Component, entity::Entity, event::{Event, EventWriter}, system::Query};
use bevy_ecs::{
component::Component,
entity::Entity,
event::{Event, EventWriter},
system::Query,
};
#[derive(Event)]
struct LevelUpEvent<T> {
@ -10,10 +15,7 @@ struct FooTask {
field: i32,
}
fn player_level_up(
mut ev_levelup: EventWriter<LevelUpEvent<i32>>,
query: Query<(Entity, &FooTask)>,
) {
fn player_level_up(mut ev_levelup: EventWriter<LevelUpEvent<i32>>, query: Query<(Entity, &FooTask)>) {
for (entity, xp) in query.iter() {
ev_levelup.write(LevelUpEvent::<i32> { inner: 5 });
}

View file

@ -1,7 +1,7 @@
use serde::{Deserialize, Serialize};
use vanth::{hash, store::Store, Vanth};
use std::path::PathBuf;
use tempfile::TempDir;
use vanth::{Vanth, hash, store::Store};
#[derive(Clone, Debug, Deserialize, Serialize, PartialEq, Vanth)]
struct Foo {
@ -18,28 +18,28 @@ fn test_sqlite_store() {
let dir = TempDir::new().unwrap();
let path = dir.path().join("test.db");
let mut store = Store::from_path(path.clone()).unwrap();
let foo_1 = Foo { inner: 1 };
let foo_2 = Foo { inner: 2 };
let bar_1 = Bar { inner: "hello".into() };
assert_eq!(store.get_all_of_type::<Foo>().unwrap().len(), 0);
assert_eq!(store.get_all_of_type::<Bar>().unwrap().len(), 0);
store.write(&foo_1).unwrap();
store.write(&foo_2).unwrap();
store.write(&bar_1).unwrap();
assert_eq!(store.get_all_of_type::<Foo>().unwrap().len(), 2);
assert_eq!(store.get_all_of_type::<Bar>().unwrap().len(), 1);
let foo_2_hash = hash(&foo_2);
let foo_2_fetched = store.get_from_hash(foo_2_hash).unwrap().unwrap();
assert_ne!(foo_1, foo_2_fetched);
assert_eq!(foo_2, foo_2_fetched);
store.delete::<Foo>(foo_2_hash).unwrap();
assert_eq!(store.get_all_of_type::<Foo>().unwrap().len(), 1);
store.delete_all::<Foo>().unwrap();
store.delete_all::<Bar>().unwrap();
assert_eq!(store.get_all_of_type::<Foo>().unwrap().len(), 0);

View file

@ -1,7 +1,7 @@
use proc_macro::TokenStream;
use quote::quote;
use syn::{parse_macro_input, DeriveInput, GenericParam, Generics};
use syn::parse_quote;
use syn::{DeriveInput, GenericParam, Generics, parse_macro_input};
#[proc_macro_derive(Vanth)]
pub fn vanth_derive(input: TokenStream) -> TokenStream {
@ -11,15 +11,19 @@ pub fn vanth_derive(input: TokenStream) -> TokenStream {
let mut generics = input.generics.clone();
let type_params: Vec<syn::Ident> = generics.params.iter().filter_map(|param| {
if let GenericParam::Type(type_param) = param {
Some(type_param.ident.clone())
} else {
None
}
}).collect();
let type_params: Vec<syn::Ident> = generics
.params
.iter()
.filter_map(|param| {
if let GenericParam::Type(type_param) = param {
Some(type_param.ident.clone())
} else {
None
}
})
.collect();
let mut where_clause = generics.where_clause.clone().unwrap_or_else(|| parse_quote!(where ));
let mut where_clause = generics.where_clause.clone().unwrap_or_else(|| parse_quote!(where));
for tp in &type_params {
where_clause.predicates.push(parse_quote!(#tp : vanth::Vanth));
}

View file

@ -1,5 +1,5 @@
use rand_core::{RngCore, SeedableRng};
use rand_chacha::ChaCha8Rng;
use rand_core::{RngCore, SeedableRng};
use serde::{Deserialize, Serialize};
use std::f32::consts::PI;
use vanth_derive::Vanth;
@ -10,11 +10,15 @@ pub struct Rng {
}
pub fn rng_new() -> Rng {
Rng { inner: ChaCha8Rng::from_seed([0u8; 32]) }
Rng {
inner: ChaCha8Rng::from_seed([0u8; 32]),
}
}
pub fn rng_from_seed(seed: [u8; 32]) -> Rng {
Rng { inner: ChaCha8Rng::from_seed(seed) }
Rng {
inner: ChaCha8Rng::from_seed(seed),
}
}
pub fn rng_set_stream(rng: &mut Rng, stream: u64) {
@ -82,7 +86,7 @@ impl From<f32> for Score {
#[derive(Clone, Debug, Deserialize, Serialize, Vanth)]
pub struct OptimizationResult {
/// List of pairs of evaluation score and Rng used to generate the value.
pub values: Vec<(Rng, f32)>
pub values: Vec<(Rng, f32)>,
}
pub fn optimize<T: Varo>(evaluator: impl Fn(T) -> Score, rng: &mut Rng, rounds: u32) -> OptimizationResult {

View file

@ -1,24 +1,24 @@
use varo::{optimize, Rng, Score, Varo};
use varo::{Rng, Score, Varo, optimize};
#[test]
fn test_optimize() {
struct Foo {
x: f32,
}
impl Varo for Foo {
fn next(digest: &mut varo::Rng) -> Self {
let x = varo::rng_gen_f32(digest) * 10.0;
Foo { x }
}
}
fn evaluate(foo: Foo) -> Score {
let x = foo.x;
let score = -0.9 * x.powi(3) + 2.6 * x.powi(2) - 4.0 * x;
score.into()
}
let mut rng = varo::rng_new();
let optimization_result = optimize(evaluate, &mut rng, 10);
assert_eq!(optimization_result.values.len(), 10);

4
rustfmt.toml Normal file
View file

@ -0,0 +1,4 @@
edition = "2024"
max_width = 120
comment_width = 120
wrap_comments = true