Skip to content

Latest commit

Β 

History

History
146 lines (93 loc) Β· 3.38 KB

File metadata and controls

146 lines (93 loc) Β· 3.38 KB

Here’s a polished README.md draft for your crate:


🧩 intern β€” Fast, memory-efficient interning for Rust

intern provides a thread-safe, memory-efficient interning system for Rust. It allows you to deduplicate repeated values (like strings, symbols, or AST nodes) by storing them once and reusing references.

Interned values have pointer identity semantics: equality and hashing are based on the underlying Arc<T> pointer, not just the value.


✨ Features

  • πŸ”’ Thread-safe β€” sharded lock-based design with low contention.
  • ⚑ Fast lookups β€” O(1) average-case insertions using FxHasher.
  • 🧹 Automatic cleanup β€” unused entries are dropped when no longer referenced.
  • πŸ“¦ Flexible β€” works with str, String, &'static str, Rc<str>, Arc<str>, Box<str>, and Cow<str>.
  • πŸ› οΈ Custom types β€” implement Internable to intern your own types.
  • πŸ”„ Serde support (optional) β€” enable with features = ["serde"].

πŸš€ Example Usage

Interning strings

use intern::Interned;

let a = Interned::from("hello");
let b = Interned::from("hello".to_string());

assert!(a.ptr_eq(&b)); // both point to the same Arc<str>

Custom internable type

use intern::{Internable, Interned, Interner};

#[derive(Eq, Hash, PartialEq)]
struct Symbol(&'static str);

impl Internable for Symbol {
    fn interner() -> &'static Interner<Self> {
        static INTERNER: Interner<Symbol> = Interner::new();
        &INTERNER
    }
}

let a = Symbol("hello").intern();
let b = Symbol("hello").intern();

assert!(a.ptr_eq(&b)); // pointer equality
assert_eq!(a, b);      // value equality still works

πŸ” API Overview

A wrapper around Arc<T> with pointer identity semantics.

  • ptr_eq(&self, &Self) -> bool β€” fast pointer comparison.
  • Implements Deref, Borrow, Eq, Hash, Clone, Serialize/Deserialize (with serde).

A trait for values that can be interned.

  • fn intern(self) -> Interned<Self> β€” interns the value.
  • fn interner() -> &'static Interner<Self> β€” provides the global interner.

Thread-safe storage of interned values.

  • intern(value) -> Interned<T> β€” deduplicates or inserts a value.
  • len() -> usize β€” number of distinct interned values.
  • is_empty() -> bool.

βš™οΈ Performance

  • Sharded HashMap reduces lock contention.
  • Intern/lookup: O(1) average-case.
  • Uses FxHasher for speed (same as rustc).
  • Automatically removes unused values when their last reference is dropped.

πŸ“¦ Installation

Add to your Cargo.toml:

[dependencies]
intern = "0.1"

Optional serde support:

[dependencies]
intern = { version = "0.1", features = ["serde"] }

πŸ§ͺ Testing

cargo test

Includes:

  • βœ… Deduplication
  • βœ… Equality & hashing
  • βœ… Automatic cleanup
  • βœ… Concurrency stress test

πŸ”’ Safety

Interned values are stored in Arc<T>s. When the last Interned<T> handle drops, the interner removes its entry, ensuring no leaks and safe reuse.


πŸ“œ License

Licensed under either of:

  • MIT License
  • Apache License, Version 2.0

at your option.