Skip to main content

Extend

Trait Extend 

Source
pub trait Extend: Functor {
    // Required method
    fn extend<A, B>(
        wa: Self::Of<A>,
        f: impl Fn(&Self::Of<A>) -> B,
    ) -> Self::Of<B>
       where A: Clone;

    // Provided method
    fn duplicate<A>(wa: Self::Of<A>) -> Self::Of<Self::Of<A>>
       where A: Clone,
             Self::Of<A>: Clone { ... }
}
Expand description

Extend: the dual of Chain. Enables cooperative “context-aware” computation.

Given a value in context W<A> and a function &W<A> -> B that can inspect the full context, extend applies that function at every “position” in the structure, producing W<B>.

Laws:

  • Associativity: extend(f, extend(g, w)) == extend(|w| f(&extend(g, w.clone())), w)

Required Methods§

Source

fn extend<A, B>(wa: Self::Of<A>, f: impl Fn(&Self::Of<A>) -> B) -> Self::Of<B>
where A: Clone,

Provided Methods§

Source

fn duplicate<A>(wa: Self::Of<A>) -> Self::Of<Self::Of<A>>
where A: Clone, Self::Of<A>: Clone,

Examples found in repository?
examples/cellular_automaton.rs (line 133)
95fn main() {
96    println!("=== Cellular Automaton Example ===\n");
97    println!("Using Extend (Comonad) to evolve a 1D cellular automaton.\n");
98
99    // Initial state: single cell in the middle of a 21-cell grid
100    let width = 21;
101    let mid = width / 2;
102    let mut cells: Vec<u8> = vec![0; width];
103    cells[mid] = 1;
104    let initial = NonEmptyVec::new(cells[0], cells[1..].to_vec());
105
106    // Rule 90 (XOR of neighbors)
107    println!("--- Rule 90 (XOR of neighbors) ---");
108    let history = evolve(initial.clone(), rule_90, 10);
109    for (i, grid) in history.iter().enumerate() {
110        println!("  {:>2}: {}", i, display_grid(grid));
111    }
112
113    // Demonstrate Comonad::extract
114    println!("\n--- Comonad::extract (read focused cell) ---");
115    println!(
116        "  Head of initial grid: {}",
117        <NonEmptyVecF as Comonad>::extract(&initial)
118    );
119
120    // Majority rule
121    println!("\n--- Majority rule ---");
122    // Start with a more interesting pattern
123    let pattern = NonEmptyVec::new(1, vec![0, 1, 1, 0, 0, 1, 0, 1, 1, 0, 1, 0, 0, 1, 0]);
124    println!("  Initial: {}", display_grid(&pattern));
125    let history = evolve(pattern, rule_majority, 8);
126    for (i, grid) in history.iter().enumerate() {
127        println!("  {:>2}: {}", i, display_grid(grid));
128    }
129
130    // Demonstrate Extend::duplicate
131    println!("\n--- Extend::duplicate (all focused views) ---");
132    let small = NonEmptyVec::new(1, vec![2, 3]);
133    let duplicated: NonEmptyVec<NonEmptyVec<u8>> = NonEmptyVecF::duplicate(small);
134    println!("  Original: [1, 2, 3]");
135    println!("  Duplicated (each row is a focused view):");
136    for (i, view) in duplicated.iter().enumerate() {
137        let cells: Vec<String> = view.iter().map(|c| c.to_string()).collect();
138        println!("    focus {}: [{}]", i, cells.join(", "));
139    }
140}

Dyn Compatibility§

This trait is not dyn compatible.

In older versions of Rust, dyn compatibility was called "object safety".

Implementors§

Source§

impl Extend for IdentityF

Source§

impl Extend for NonEmptyVecF

Available on crate features alloc or std only.
Source§

impl Extend for OptionF

Source§

impl<E> Extend for EnvF<E>

Source§

impl<F> Extend for CofreeF<F>
where F: HKT + Functor,