https://github.com/zeramorphic/flat-drop
https://github.com/zeramorphic/flat-drop
Last synced: 4 months ago
JSON representation
- Host: GitHub
- URL: https://github.com/zeramorphic/flat-drop
- Owner: zeramorphic
- Created: 2025-04-02T12:11:35.000Z (7 months ago)
- Default Branch: main
- Last Pushed: 2025-06-24T16:29:30.000Z (4 months ago)
- Last Synced: 2025-06-24T16:46:04.672Z (4 months ago)
- Language: Rust
- Size: 12.7 KB
- Stars: 1
- Watchers: 1
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
Awesome Lists containing this project
README
# Flat drop
In this crate, we define the `FlatDrop` type.
`FlatDrop` behaves just like a `K`, but with a custom `Drop` implementation
that avoids blowing up the stack when dropping large objects.
Instead of recursively dropping subobjects, we perform a depth-first search
and iteratively drop subobjects.
To use this crate, you can replace recursive `Box`es and `Arc`s in your types
with `FlatDrop>` or `FlatDrop>`. You'll need to implement the
`Recursive` trait for your type, which performs one step of the iterative
dropping procedure.
This crate uses `unsafe` internally, but the external API is safe.
# Example
```rs
use flat_drop::{FlatDrop, Recursive};
/// Peano natural numbers.
enum Natural {
Zero,
Succ(FlatDrop>),
}
impl Recursive for Natural {
type Container = Box;
fn destruct(self) -> impl Iterator {
match self {
Natural::Zero => None,
Natural::Succ(pred) => Some(pred.into_inner()),
}
.into_iter()
}
}
impl Natural {
pub fn from_usize(value: usize) -> Self {
(0..value).fold(Self::Zero, |nat, _| {
Self::Succ(FlatDrop::new(Box::new(nat)))
})
}
}
// Create a new thread with a 4kb stack and allocate a number far bigger than 4 * 1024.
const STACK_SIZE: usize = 4 * 1024;
fn task() {
let nat = Natural::from_usize(STACK_SIZE * 100);
drop(std::hint::black_box(nat));
}
std::thread::Builder::new()
.stack_size(STACK_SIZE)
.spawn(task)
.unwrap()
.join()
.unwrap();
```