prism3_function/functions/
mutating_function.rs

1/*******************************************************************************
2 *
3 *    Copyright (c) 2025.
4 *    3-Prism Co. Ltd.
5 *
6 *    All rights reserved.
7 *
8 ******************************************************************************/
9//! # MutatingFunction Types
10//!
11//! Provides Java-like `MutatingFunction` interface implementations for
12//! performing operations that accept a mutable reference and return a result.
13//!
14//! It is similar to the `Fn(&mut T) -> R` trait in the standard library.
15//!
16//! This module provides a unified `MutatingFunction` trait and three concrete
17//! implementations based on different ownership models:
18//!
19//! - **`BoxMutatingFunction<T, R>`**: Box-based single ownership
20//!   implementation
21//! - **`ArcMutatingFunction<T, R>`**: Arc-based thread-safe shared ownership
22//!   implementation
23//! - **`RcMutatingFunction<T, R>`**: Rc-based single-threaded shared
24//!   ownership implementation
25//!
26//! # Design Philosophy
27//!
28//! `MutatingFunction` bridges the gap between `Function` and `Mutator`:
29//!
30//! - **Function**: `Fn(&T) -> R` - reads input, returns result
31//! - **Mutator**: `Fn(&mut T)` - modifies input, no return
32//! - **MutatingFunction**: `Fn(&mut T) -> R` - modifies input AND returns
33//!   result
34//!
35//! ## Comparison with Related Types
36//!
37//! | Type | Input | Modifies? | Returns? | Use Cases |
38//! |------|-------|-----------|----------|-----------|
39//! | **Function** | `&T` | ❌ | ✅ | Read-only transform |
40//! | **Mutator** | `&mut T` | ✅ | ❌ | In-place modification |
41//! | **MutatingFunction** | `&mut T` | ✅ | ✅ | Modify + return info |
42//! | **Transformer** | `T` | N/A | ✅ | Consume + transform |
43//!
44//! **Key Insight**: Use `MutatingFunction` when you need to both modify the
45//! input and return information about the modification or the previous state.
46//!
47//! # Comparison Table
48//!
49//! | Feature          | Box | Arc | Rc |
50//! |------------------|-----|-----|----|
51//! | Ownership        | Single | Shared | Shared |
52//! | Cloneable        | ❌ | ✅ | ✅ |
53//! | Thread-Safe      | ❌ | ✅ | ❌ |
54//! | Interior Mut.    | N/A | N/A | N/A |
55//! | `and_then` API   | `self` | `&self` | `&self` |
56//! | Lock Overhead    | None | None | None |
57//!
58//! # Use Cases
59//!
60//! ## Common Scenarios
61//!
62//! - **Atomic operations**: Increment counter and return new value
63//! - **Cache updates**: Update cache and return old value
64//! - **Validation**: Validate and fix data, return validation result
65//! - **Event handlers**: Process event and return whether to continue
66//! - **State machines**: Transition state and return transition info
67//!
68//! # Examples
69//!
70//! ## Basic Usage
71//!
72//! ```rust
73//! use prism3_function::{BoxMutatingFunction, MutatingFunction};
74//!
75//! // Increment counter and return new value
76//! let incrementer = BoxMutatingFunction::new(|x: &mut i32| {
77//!     *x += 1;
78//!     *x
79//! });
80//!
81//! let mut value = 5;
82//! let result = incrementer.apply(&mut value);
83//! assert_eq!(value, 6);
84//! assert_eq!(result, 6);
85//! ```
86//!
87//! ## Method Chaining
88//!
89//! ```rust
90//! use prism3_function::{BoxMutatingFunction, MutatingFunction};
91//!
92//! let chained = BoxMutatingFunction::new(|x: &mut i32| {
93//!     *x *= 2;
94//!     *x
95//! })
96//! .and_then(|x: &mut i32| {
97//!     *x += 10;
98//!     *x
99//! });
100//!
101//! let mut value = 5;
102//! let result = chained.apply(&mut value);
103//! assert_eq!(value, 20); // (5 * 2) + 10
104//! assert_eq!(result, 20);
105//! ```
106//!
107//! ## Cache Update Pattern
108//!
109//! ```rust
110//! use prism3_function::{BoxMutatingFunction, MutatingFunction};
111//! use std::collections::HashMap;
112//!
113//! let updater = BoxMutatingFunction::new(
114//!     |cache: &mut HashMap<String, i32>| {
115//!         cache.insert("key".to_string(), 42)
116//!     }
117//! );
118//!
119//! let mut cache = HashMap::new();
120//! cache.insert("key".to_string(), 10);
121//! let old_value = updater.apply(&mut cache);
122//! assert_eq!(old_value, Some(10));
123//! assert_eq!(cache.get("key"), Some(&42));
124//! ```
125//!
126//! # Author
127//!
128//! Haixing Hu
129use std::rc::Rc;
130use std::sync::Arc;
131
132use crate::functions::{
133    function::Function,
134    macros::{
135        impl_box_conditional_function,
136        impl_box_function_methods,
137        impl_conditional_function_clone,
138        impl_conditional_function_debug_display,
139        impl_fn_ops_trait,
140        impl_function_clone,
141        impl_function_common_methods,
142        impl_function_debug_display,
143        impl_function_identity_method,
144        impl_shared_conditional_function,
145        impl_shared_function_methods,
146    },
147    mutating_function_once::BoxMutatingFunctionOnce,
148};
149use crate::macros::{
150    impl_arc_conversions,
151    impl_box_conversions,
152    impl_closure_trait,
153    impl_rc_conversions,
154};
155use crate::predicates::predicate::{
156    ArcPredicate,
157    BoxPredicate,
158    Predicate,
159    RcPredicate,
160};
161
162// =======================================================================
163// 1. MutatingFunction Trait - Unified Interface
164// =======================================================================
165
166/// MutatingFunction trait - Unified mutating function interface
167///
168/// It is similar to the `Fn(&mut T) -> R` trait in the standard library.
169///
170/// Defines the core behavior of all mutating function types. Performs
171/// operations that accept a mutable reference, potentially modify it, and
172/// return a result.
173///
174/// This trait is automatically implemented by:
175/// - All closures implementing `Fn(&mut T) -> R`
176/// - `BoxMutatingFunction<T, R>`, `ArcMutatingFunction<T, R>`, and
177///   `RcMutatingFunction<T, R>`
178///
179/// # Design Rationale
180///
181/// The trait provides a unified abstraction over different ownership models
182/// for operations that both modify input and return results. This is useful
183/// for scenarios where you need to:
184/// - Update state and return information about the update
185/// - Perform atomic-like operations (modify and return)
186/// - Implement event handlers that modify state and signal continuation
187///
188/// # Features
189///
190/// - **Unified Interface**: All mutating function types share the same
191///   `apply` method signature
192/// - **Automatic Implementation**: Closures automatically implement this
193///   trait
194/// - **Type Conversions**: Easy conversion between ownership models
195/// - **Generic Programming**: Write functions that work with any mutating
196///   function type
197///
198/// # Examples
199///
200/// ## Generic Function
201///
202/// ```rust
203/// use prism3_function::{MutatingFunction, BoxMutatingFunction};
204///
205/// fn apply_and_log<F: MutatingFunction<i32, i32>>(
206///     func: &F,
207///     value: i32
208/// ) -> i32 {
209///     let mut val = value;
210///     let result = func.apply(&mut val);
211///     println!("Modified: {} -> {}, returned: {}", value, val, result);
212///     result
213/// }
214///
215/// let incrementer = BoxMutatingFunction::new(|x: &mut i32| {
216///     *x += 1;
217///     *x
218/// });
219/// assert_eq!(apply_and_log(&incrementer, 5), 6);
220/// ```
221///
222/// ## Type Conversion
223///
224/// ```rust
225/// use prism3_function::MutatingFunction;
226///
227/// let closure = |x: &mut i32| {
228///     *x *= 2;
229///     *x
230/// };
231///
232/// // Convert to different ownership models
233/// let box_func = closure.into_box();
234/// // let rc_func = closure.into_rc();  // closure moved
235/// // let arc_func = closure.into_arc(); // closure moved
236/// ```
237///
238/// # Author
239///
240/// Haixing Hu
241pub trait MutatingFunction<T, R> {
242    /// Applies the function to the mutable reference and returns a result
243    ///
244    /// Executes an operation on the given mutable reference, potentially
245    /// modifying it, and returns a result value.
246    ///
247    /// # Parameters
248    ///
249    /// * `t` - A mutable reference to the input value
250    ///
251    /// # Returns
252    ///
253    /// The computed result value
254    ///
255    /// # Examples
256    ///
257    /// ```rust
258    /// use prism3_function::{MutatingFunction, BoxMutatingFunction};
259    ///
260    /// let func = BoxMutatingFunction::new(|x: &mut i32| {
261    ///     let old = *x;
262    ///     *x += 1;
263    ///     old
264    /// });
265    ///
266    /// let mut value = 5;
267    /// let old_value = func.apply(&mut value);
268    /// assert_eq!(old_value, 5);
269    /// assert_eq!(value, 6);
270    /// ```
271    fn apply(&self, t: &mut T) -> R;
272
273    /// Convert this mutating function into a `BoxMutatingFunction<T, R>`.
274    ///
275    /// This consuming conversion takes ownership of `self` and returns a
276    /// boxed implementation that forwards calls to the original function.
277    /// Types that can provide a more efficient conversion may override the
278    /// default implementation.
279    ///
280    /// # Consumption
281    ///
282    /// This method consumes the function: the original value will no longer
283    /// be available after the call. For cloneable functions call `.clone()`
284    /// before converting if you need to retain the original instance.
285    ///
286    /// # Returns
287    ///
288    /// A `BoxMutatingFunction<T, R>` that forwards to the original function.
289    ///
290    /// # Examples
291    ///
292    /// ```rust
293    /// use prism3_function::MutatingFunction;
294    ///
295    /// let closure = |x: &mut i32| {
296    ///     *x *= 2;
297    ///     *x
298    /// };
299    /// let mut boxed = closure.into_box();
300    /// let mut value = 5;
301    /// assert_eq!(boxed.apply(&mut value), 10);
302    /// ```
303    fn into_box(self) -> BoxMutatingFunction<T, R>
304    where
305        Self: Sized + 'static,
306        T: 'static,
307        R: 'static,
308    {
309        BoxMutatingFunction::new(move |t| self.apply(t))
310    }
311
312    /// Convert this mutating function into an `RcMutatingFunction<T, R>`.
313    ///
314    /// This consuming conversion takes ownership of `self` and returns an
315    /// `Rc`-backed function that forwards calls to the original. Override to
316    /// provide a more direct or efficient conversion when available.
317    ///
318    /// # Consumption
319    ///
320    /// This method consumes the function. If you need to keep the original
321    /// instance, clone it prior to calling this method.
322    ///
323    /// # Returns
324    ///
325    /// An `RcMutatingFunction<T, R>` forwarding to the original function.
326    ///
327    /// # Examples
328    ///
329    /// ```rust
330    /// use prism3_function::MutatingFunction;
331    ///
332    /// let closure = |x: &mut i32| {
333    ///     *x *= 2;
334    ///     *x
335    /// };
336    /// let mut rc = closure.into_rc();
337    /// let mut value = 5;
338    /// assert_eq!(rc.apply(&mut value), 10);
339    /// ```
340    fn into_rc(self) -> RcMutatingFunction<T, R>
341    where
342        Self: Sized + 'static,
343        T: 'static,
344        R: 'static,
345    {
346        RcMutatingFunction::new(move |t| self.apply(t))
347    }
348
349    /// Convert this mutating function into an `ArcMutatingFunction<T, R>`.
350    ///
351    /// This consuming conversion takes ownership of `self` and returns an
352    /// `Arc`-wrapped, thread-safe function. Types may override the default
353    /// implementation to provide a more efficient conversion.
354    ///
355    /// # Consumption
356    ///
357    /// This method consumes the function. Clone the instance first if you
358    /// need to retain the original for further use.
359    ///
360    /// # Returns
361    ///
362    /// An `ArcMutatingFunction<T, R>` that forwards to the original
363    /// function.
364    ///
365    /// # Examples
366    ///
367    /// ```rust
368    /// use prism3_function::MutatingFunction;
369    ///
370    /// let closure = |x: &mut i32| {
371    ///     *x *= 2;
372    ///     *x
373    /// };
374    /// let mut arc = closure.into_arc();
375    /// let mut value = 5;
376    /// assert_eq!(arc.apply(&mut value), 10);
377    /// ```
378    fn into_arc(self) -> ArcMutatingFunction<T, R>
379    where
380        Self: Sized + Send + Sync + 'static,
381        T: Send + 'static,
382        R: Send + 'static,
383    {
384        ArcMutatingFunction::new(move |t| self.apply(t))
385    }
386
387    /// Consume the function and return an `Fn(&mut T) -> R` closure.
388    ///
389    /// The returned closure forwards calls to the original function and is
390    /// suitable for use with iterator adapters or other contexts expecting
391    /// closures.
392    ///
393    /// # Consumption
394    ///
395    /// This method consumes the function. The original instance will not be
396    /// available after calling this method.
397    ///
398    /// # Returns
399    ///
400    /// A closure implementing `Fn(&mut T) -> R` which forwards to the
401    /// original function.
402    ///
403    /// # Examples
404    ///
405    /// ```rust
406    /// use prism3_function::{MutatingFunction, BoxMutatingFunction};
407    ///
408    /// let func = BoxMutatingFunction::new(|x: &mut i32| {
409    ///     *x *= 2;
410    ///     *x
411    /// });
412    /// let closure = func.into_fn();
413    /// let mut value = 5;
414    /// assert_eq!(closure(&mut value), 10);
415    /// ```
416    fn into_fn(self) -> impl Fn(&mut T) -> R
417    where
418        Self: Sized + 'static,
419        T: 'static,
420        R: 'static,
421    {
422        move |t| self.apply(t)
423    }
424
425    /// Convert to MutatingFunctionOnce
426    ///
427    /// **⚠️ Consumes `self`**: The original function will be unavailable
428    /// after calling this method.
429    ///
430    /// Converts a reusable mutating function to a one-time function that
431    /// consumes itself on use. This enables passing `MutatingFunction` to
432    /// functions that require `MutatingFunctionOnce`.
433    ///
434    /// # Returns
435    ///
436    /// Returns a `BoxMutatingFunctionOnce<T, R>`
437    ///
438    /// # Examples
439    ///
440    /// ```rust
441    /// use prism3_function::{MutatingFunctionOnce, MutatingFunction,
442    ///                       BoxMutatingFunction};
443    ///
444    /// fn takes_once<F: MutatingFunctionOnce<i32, i32>>(func: F, value: &mut i32) {
445    ///     let result = func.apply(value);
446    ///     println!("Result: {}", result);
447    /// }
448    ///
449    /// let func = BoxMutatingFunction::new(|x: &mut i32| {
450    ///     *x *= 2;
451    ///     *x
452    /// });
453    /// let mut value = 5;
454    /// takes_once(func.into_once(), &mut value);
455    /// ```
456    fn into_once(self) -> BoxMutatingFunctionOnce<T, R>
457    where
458        Self: Sized + 'static,
459        T: 'static,
460        R: 'static,
461    {
462        BoxMutatingFunctionOnce::new(move |t| self.apply(t))
463    }
464
465    /// Create a non-consuming `BoxMutatingFunction<T, R>` that forwards to
466    /// `self`.
467    ///
468    /// The default implementation clones `self` (requires `Clone`) and
469    /// returns a boxed function that calls the cloned instance. Override this
470    /// method if a more efficient conversion exists.
471    ///
472    /// # Returns
473    ///
474    /// A `BoxMutatingFunction<T, R>` that forwards to a clone of `self`.
475    fn to_box(&self) -> BoxMutatingFunction<T, R>
476    where
477        Self: Sized + Clone + 'static,
478        T: 'static,
479        R: 'static,
480    {
481        self.clone().into_box()
482    }
483
484    /// Create a non-consuming `RcMutatingFunction<T, R>` that forwards to
485    /// `self`.
486    ///
487    /// The default implementation clones `self` (requires `Clone`) and
488    /// returns an `Rc`-backed function that forwards calls to the clone.
489    /// Override to provide a more direct or efficient conversion if needed.
490    ///
491    /// # Returns
492    ///
493    /// An `RcMutatingFunction<T, R>` that forwards to a clone of `self`.
494    fn to_rc(&self) -> RcMutatingFunction<T, R>
495    where
496        Self: Sized + Clone + 'static,
497        T: 'static,
498        R: 'static,
499    {
500        self.clone().into_rc()
501    }
502
503    /// Create a non-consuming `ArcMutatingFunction<T, R>` that forwards to
504    /// `self`.
505    ///
506    /// The default implementation clones `self` (requires
507    /// `Clone + Send + Sync`) and returns an `Arc`-wrapped function that
508    /// forwards calls to the clone. Override when a more efficient conversion
509    /// is available.
510    ///
511    /// # Returns
512    ///
513    /// An `ArcMutatingFunction<T, R>` that forwards to a clone of `self`.
514    fn to_arc(&self) -> ArcMutatingFunction<T, R>
515    where
516        Self: Sized + Clone + Send + Sync + 'static,
517        T: Send + 'static,
518        R: Send + 'static,
519    {
520        self.clone().into_arc()
521    }
522
523    /// Create a boxed `Fn(&mut T) -> R` closure that forwards to `self`.
524    ///
525    /// The default implementation clones `self` (requires `Clone`) and
526    /// returns a boxed closure that invokes the cloned instance. Override to
527    /// provide a more efficient conversion when possible.
528    ///
529    /// # Returns
530    ///
531    /// A closure implementing `Fn(&mut T) -> R` which forwards to the
532    /// original function.
533    fn to_fn(&self) -> impl Fn(&mut T) -> R
534    where
535        Self: Sized + Clone + 'static,
536        T: 'static,
537        R: 'static,
538    {
539        self.clone().into_fn()
540    }
541
542    /// Convert to MutatingFunctionOnce without consuming self
543    ///
544    /// **⚠️ Requires Clone**: This method requires `Self` to implement `Clone`.
545    /// Clones the current function and converts the clone to a one-time function.
546    ///
547    /// # Returns
548    ///
549    /// Returns a `BoxMutatingFunctionOnce<T, R>`
550    ///
551    /// # Examples
552    ///
553    /// ```rust
554    /// use prism3_function::{MutatingFunctionOnce, MutatingFunction,
555    ///                       BoxMutatingFunction};
556    ///
557    /// fn takes_once<F: MutatingFunctionOnce<i32, i32>>(func: F, value: &mut i32) {
558    ///     let result = func.apply(value);
559    ///     println!("Result: {}", result);
560    /// }
561    ///
562    /// let func = BoxMutatingFunction::new(|x: &mut i32| {
563    ///     *x *= 2;
564    ///     *x
565    /// });
566    /// let mut value = 5;
567    /// takes_once(func.to_once(), &mut value);
568    /// ```
569    fn to_once(&self) -> BoxMutatingFunctionOnce<T, R>
570    where
571        Self: Clone + 'static,
572        T: 'static,
573        R: 'static,
574    {
575        self.clone().into_once()
576    }
577}
578
579// =======================================================================
580// 3. BoxMutatingFunction - Single Ownership Implementation
581// =======================================================================
582
583/// BoxMutatingFunction struct
584///
585/// A mutating function implementation based on `Box<dyn Fn(&mut T) -> R>`
586/// for single ownership scenarios. This is the simplest and most efficient
587/// mutating function type when sharing is not required.
588///
589/// # Features
590///
591/// - **Single Ownership**: Not cloneable, ownership moves on use
592/// - **Zero Overhead**: No reference counting or locking
593/// - **Stateless**: Cannot modify captured environment (uses `Fn` not
594///   `FnMut`)
595/// - **Builder Pattern**: Method chaining consumes `self` naturally
596/// - **Factory Methods**: Convenient constructors for common patterns
597///
598/// # Use Cases
599///
600/// Choose `BoxMutatingFunction` when:
601/// - The function is used for stateless operations
602/// - Building pipelines where ownership naturally flows
603/// - No need to share the function across contexts
604/// - Performance is critical and no sharing overhead is acceptable
605///
606/// # Performance
607///
608/// `BoxMutatingFunction` has the best performance among the three function
609/// types:
610/// - No reference counting overhead
611/// - No lock acquisition or runtime borrow checking
612/// - Direct function call through vtable
613/// - Minimal memory footprint (single pointer)
614///
615/// # Examples
616///
617/// ```rust
618/// use prism3_function::{MutatingFunction, BoxMutatingFunction};
619///
620/// let func = BoxMutatingFunction::new(|x: &mut i32| {
621///     *x *= 2;
622///     *x
623/// });
624/// let mut value = 5;
625/// assert_eq!(func.apply(&mut value), 10);
626/// assert_eq!(value, 10);
627/// ```
628///
629/// # Author
630///
631/// Haixing Hu
632pub struct BoxMutatingFunction<T, R> {
633    function: Box<dyn Fn(&mut T) -> R>,
634    name: Option<String>,
635}
636
637impl<T, R> BoxMutatingFunction<T, R>
638where
639    T: 'static,
640    R: 'static,
641{
642    // Generates: new(), new_with_name(), new_with_optional_name(), name(), set_name()
643    impl_function_common_methods!(
644        BoxMutatingFunction<T, R>,
645        (Fn(&mut T) -> R + 'static),
646        |f| Box::new(f)
647    );
648
649    // Generates: when(), and_then(), compose()
650    impl_box_function_methods!(
651        BoxMutatingFunction<T, R>,
652        BoxConditionalMutatingFunction,
653        Function  // chains a non-mutating function after this mutating function
654    );
655}
656
657// Generates: Debug and Display implementations for BoxMutatingFunction<T, R>
658impl_function_debug_display!(BoxMutatingFunction<T, R>);
659
660// Generates: identity() method for BoxMutatingFunction<T, T>
661impl_function_identity_method!(BoxMutatingFunction<T, T>, mutating);
662
663// Implement MutatingFunction trait for BoxMutatingFunction<T, R>
664impl<T, R> MutatingFunction<T, R> for BoxMutatingFunction<T, R> {
665    fn apply(&self, t: &mut T) -> R {
666        (self.function)(t)
667    }
668
669    // Generates: into_box(), into_rc(), into_fn(), into_once()
670    impl_box_conversions!(
671        BoxMutatingFunction<T, R>,
672        RcMutatingFunction,
673        Fn(&mut T) -> R,
674        BoxMutatingFunctionOnce
675    );
676}
677
678// =======================================================================
679// 4. RcMutatingFunction - Single-Threaded Shared Ownership
680// =======================================================================
681
682/// RcMutatingFunction struct
683///
684/// A mutating function implementation based on `Rc<dyn Fn(&mut T) -> R>` for
685/// single-threaded shared ownership scenarios. This type allows multiple
686/// references to the same function without the overhead of thread safety.
687///
688/// # Features
689///
690/// - **Shared Ownership**: Cloneable via `Rc`, multiple owners allowed
691/// - **Single-Threaded**: Not thread-safe, cannot be sent across threads
692/// - **Stateless**: Cannot modify captured environment (uses `Fn` not
693///   `FnMut`)
694/// - **Chainable**: Method chaining via `&self` (non-consuming)
695/// - **Performance**: More efficient than `ArcMutatingFunction` (no locking)
696///
697/// # Use Cases
698///
699/// Choose `RcMutatingFunction` when:
700/// - The function needs to be shared within a single thread for stateless
701///   operations
702/// - Thread safety is not required
703/// - Performance is important (avoiding lock overhead)
704///
705/// # Examples
706///
707/// ```rust
708/// use prism3_function::{MutatingFunction, RcMutatingFunction};
709///
710/// let func = RcMutatingFunction::new(|x: &mut i32| {
711///     *x *= 2;
712///     *x
713/// });
714/// let clone = func.clone();
715///
716/// let mut value = 5;
717/// assert_eq!(func.apply(&mut value), 10);
718/// ```
719///
720/// # Author
721///
722/// Haixing Hu
723pub struct RcMutatingFunction<T, R> {
724    function: Rc<dyn Fn(&mut T) -> R>,
725    name: Option<String>,
726}
727
728impl<T, R> RcMutatingFunction<T, R>
729where
730    T: 'static,
731    R: 'static,
732{
733    // Generates: new(), new_with_name(), new_with_optional_name(), name(), set_name()
734    impl_function_common_methods!(
735        RcMutatingFunction<T, R>,
736        (Fn(&mut T) -> R + 'static),
737        |f| Rc::new(f)
738    );
739
740    // Generates: when(), and_then(), compose()
741    impl_shared_function_methods!(
742        RcMutatingFunction<T, R>,
743        RcConditionalMutatingFunction,
744        into_rc,
745        Function,  // chains a non-mutating function after this mutating function
746        'static
747    );
748}
749
750// Generates: Clone implementation for RcMutatingFunction<T, R>
751impl_function_clone!(RcMutatingFunction<T, R>);
752
753// Generates: Debug and Display implementations for RcMutatingFunction<T, R>
754impl_function_debug_display!(RcMutatingFunction<T, R>);
755
756// Generates: identity() method for RcMutatingFunction<T, T>
757impl_function_identity_method!(RcMutatingFunction<T, T>, mutating);
758
759impl<T, R> MutatingFunction<T, R> for RcMutatingFunction<T, R> {
760    fn apply(&self, input: &mut T) -> R {
761        (self.function)(input)
762    }
763
764    // Use macro to implement conversion methods
765    impl_rc_conversions!(
766        RcMutatingFunction<T, R>,
767        BoxMutatingFunction,
768        BoxMutatingFunctionOnce,
769        Fn(input: &mut T) -> R
770    );
771}
772
773// =======================================================================
774// 5. ArcMutatingFunction - Thread-Safe Shared Ownership
775// =======================================================================
776
777/// ArcMutatingFunction struct
778///
779/// A mutating function implementation based on
780/// `Arc<dyn Fn(&mut T) -> R + Send + Sync>` for thread-safe shared ownership
781/// scenarios. This type allows the function to be safely shared and used
782/// across multiple threads.
783///
784/// # Features
785///
786/// - **Shared Ownership**: Cloneable via `Arc`, multiple owners allowed
787/// - **Thread-Safe**: Implements `Send + Sync`, safe for concurrent use
788/// - **Stateless**: Cannot modify captured environment (uses `Fn` not
789///   `FnMut`)
790/// - **Chainable**: Method chaining via `&self` (non-consuming)
791///
792/// # Use Cases
793///
794/// Choose `ArcMutatingFunction` when:
795/// - The function needs to be shared across multiple threads for stateless
796///   operations
797/// - Concurrent task processing (e.g., thread pools)
798/// - Thread safety is required (Send + Sync)
799///
800/// # Examples
801///
802/// ```rust
803/// use prism3_function::{MutatingFunction, ArcMutatingFunction};
804///
805/// let func = ArcMutatingFunction::new(|x: &mut i32| {
806///     *x *= 2;
807///     *x
808/// });
809/// let clone = func.clone();
810///
811/// let mut value = 5;
812/// assert_eq!(func.apply(&mut value), 10);
813/// ```
814///
815/// # Author
816///
817/// Haixing Hu
818pub struct ArcMutatingFunction<T, R> {
819    function: Arc<dyn Fn(&mut T) -> R + Send + Sync>,
820    name: Option<String>,
821}
822
823impl<T, R> ArcMutatingFunction<T, R>
824where
825    T: 'static,
826    R: 'static,
827{
828    // Generates: new(), new_with_name(), new_with_optional_name(), name(), set_name()
829    impl_function_common_methods!(
830        ArcMutatingFunction<T, R>,
831        (Fn(&mut T) -> R + Send + Sync + 'static),
832        |f| Arc::new(f)
833    );
834
835    // Generates: when(), and_then(), compose()
836    impl_shared_function_methods!(
837        ArcMutatingFunction<T, R>,
838        ArcConditionalMutatingFunction,
839        into_arc,
840        Function,  // chains a non-mutating function after this mutating function
841        Send + Sync + 'static
842    );
843}
844
845// Generates: Clone implementation for ArcMutatingFunction<T, R>
846impl_function_clone!(ArcMutatingFunction<T, R>);
847
848// Generates: Debug and Display implementations for ArcMutatingFunction<T, R>
849impl_function_debug_display!(ArcMutatingFunction<T, R>);
850
851// Generates: identity() method for ArcMutatingFunction<T, T>
852impl_function_identity_method!(ArcMutatingFunction<T, T>, mutating);
853
854impl<T, R> MutatingFunction<T, R> for ArcMutatingFunction<T, R> {
855    fn apply(&self, input: &mut T) -> R {
856        (self.function)(input)
857    }
858
859    // Use macro to implement conversion methods
860    impl_arc_conversions!(
861        ArcMutatingFunction<T, R>,
862        BoxMutatingFunction,
863        RcMutatingFunction,
864        BoxMutatingFunctionOnce,
865        Fn(input: &mut T) -> R
866    );
867}
868
869// =======================================================================
870// 6. Implement MutatingFunction trait for closures
871// =======================================================================
872
873impl_closure_trait!(
874    MutatingFunction<T, R>,
875    apply,
876    BoxMutatingFunctionOnce,
877    Fn(input: &mut T) -> R
878);
879
880// =======================================================================
881// 7. Provide extension methods for closures
882// =======================================================================
883
884// Generates: FnFunctionOps trait and blanket implementation
885impl_fn_ops_trait!(
886    (Fn(&mut T) -> R),
887    FnMutatingFunctionOps,
888    BoxMutatingFunction,
889    Function, // chains a non-mutating function after this mutating function
890    BoxConditionalMutatingFunction
891);
892
893// ============================================================================
894// BoxConditionalMutatingFunction - Box-based Conditional Mutating Function
895// ============================================================================
896
897/// BoxConditionalMutatingFunction struct
898///
899/// A conditional function that only executes when a predicate is satisfied.
900/// Uses `BoxMutatingFunction` and `BoxPredicate` for single ownership semantics.
901///
902/// This type is typically created by calling `BoxMutatingFunction::when()` and is
903/// designed to work with the `or_else()` method to create if-then-else logic.
904///
905/// # Features
906///
907/// - **Single Ownership**: Not cloneable, consumes `self` on use
908/// - **Conditional Execution**: Only transforms when predicate returns `true`
909/// - **Chainable**: Can add `or_else` branch to create if-then-else logic
910/// - **Implements Function**: Can be used anywhere a `Function` is expected
911///
912/// # Examples
913///
914/// ## With or_else Branch
915///
916/// ```rust
917/// use prism3_function::{MutatingFunction, BoxMutatingFunction};
918///
919/// let double = BoxMutatingFunction::new(|x: &mut i32| x * 2);
920/// let negate = BoxMutatingFunction::new(|x: &mut i32| -x);
921/// let conditional = double.when(|x: &i32| *x > 0).or_else(negate);
922///
923/// assert_eq!(conditional.apply(5), 10); // when branch executed
924/// assert_eq!(conditional.apply(-5), 5); // or_else branch executed
925/// ```
926///
927/// # Author
928///
929/// Haixing Hu
930pub struct BoxConditionalMutatingFunction<T, R> {
931    function: BoxMutatingFunction<T, R>,
932    predicate: BoxPredicate<T>,
933}
934
935// Use macro to generate conditional function implementations
936impl_box_conditional_function!(
937    BoxConditionalMutatingFunction<T, R>,
938    BoxMutatingFunction,
939    MutatingFunction
940);
941
942// Use macro to generate conditional function debug and display implementations
943impl_conditional_function_debug_display!(BoxConditionalMutatingFunction<T, R>);
944
945// ============================================================================
946// RcConditionalMutatingFunction - Rc-based Conditional Mutating Function
947// ============================================================================
948
949/// RcConditionalMutatingFunction struct
950///
951/// A single-threaded conditional function that only executes when a
952/// predicate is satisfied. Uses `RcMutatingFunction` and `RcPredicate` for shared
953/// ownership within a single thread.
954///
955/// This type is typically created by calling `RcMutatingFunction::when()` and is
956/// designed to work with the `or_else()` method to create if-then-else logic.
957///
958/// # Features
959///
960/// - **Shared Ownership**: Cloneable via `Rc`, multiple owners allowed
961/// - **Single-Threaded**: Not thread-safe, cannot be sent across threads
962/// - **Conditional Execution**: Only transforms when predicate returns `true`
963/// - **No Lock Overhead**: More efficient than `ArcConditionalFunction`
964///
965/// # Examples
966///
967/// ```rust
968/// use prism3_function::{MutatingFunction, RcMutatingFunction};
969///
970/// let double = RcMutatingFunction::new(|x: &mut i32| x * 2);
971/// let identity = RcMutatingFunction::<i32, i32>::identity();
972/// let conditional = double.when(|x: &i32| *x > 0).or_else(identity);
973///
974/// let conditional_clone = conditional.clone();
975///
976/// assert_eq!(conditional.apply(5), 10);
977/// assert_eq!(conditional_clone.apply(-5), -5);
978/// ```
979///
980/// # Author
981///
982/// Haixing Hu
983pub struct RcConditionalMutatingFunction<T, R> {
984    function: RcMutatingFunction<T, R>,
985    predicate: RcPredicate<T>,
986}
987
988// Use macro to generate conditional function implementations
989impl_shared_conditional_function!(
990    RcConditionalMutatingFunction<T, R>,
991    RcMutatingFunction,
992    MutatingFunction,
993    'static
994);
995
996// Use macro to generate conditional function clone implementations
997impl_conditional_function_clone!(RcConditionalMutatingFunction<T, R>);
998
999// Use macro to generate conditional function debug and display implementations
1000impl_conditional_function_debug_display!(RcConditionalMutatingFunction<T, R>);
1001
1002// ============================================================================
1003// ArcConditionalMutatingFunction - Arc-based Conditional Mutating Function
1004// ============================================================================
1005
1006/// ArcConditionalMutatingFunction struct
1007///
1008/// A thread-safe conditional function that only executes when a predicate is
1009/// satisfied. Uses `ArcMutatingFunction` and `ArcPredicate` for shared ownership
1010/// across threads.
1011///
1012/// This type is typically created by calling `ArcMutatingFunction::when()` and is
1013/// designed to work with the `or_else()` method to create if-then-else logic.
1014///
1015/// # Features
1016///
1017/// - **Shared Ownership**: Cloneable via `Arc`, multiple owners allowed
1018/// - **Thread-Safe**: Implements `Send + Sync`, safe for concurrent use
1019/// - **Conditional Execution**: Only transforms when predicate returns `true`
1020/// - **Chainable**: Can add `or_else` branch to create if-then-else logic
1021///
1022/// # Examples
1023///
1024/// ```rust
1025/// use prism3_function::{MutatingFunction, ArcMutatingFunction};
1026///
1027/// let double = ArcMutatingFunction::new(|x: &mut i32| x * 2);
1028/// let identity = ArcMutatingFunction::<i32, i32>::identity();
1029/// let conditional = double.when(|x: &i32| *x > 0).or_else(identity);
1030///
1031/// let conditional_clone = conditional.clone();
1032///
1033/// assert_eq!(conditional.apply(5), 10);
1034/// assert_eq!(conditional_clone.apply(-5), -5);
1035/// ```
1036///
1037/// # Author
1038///
1039/// Haixing Hu
1040pub struct ArcConditionalMutatingFunction<T, R> {
1041    function: ArcMutatingFunction<T, R>,
1042    predicate: ArcPredicate<T>,
1043}
1044
1045// Use macro to generate conditional function implementations
1046impl_shared_conditional_function!(
1047    ArcConditionalMutatingFunction<T, R>,
1048    ArcMutatingFunction,
1049    MutatingFunction,
1050    Send + Sync + 'static
1051);
1052
1053// Use macro to generate conditional function clone implementations
1054impl_conditional_function_clone!(ArcConditionalMutatingFunction<T, R>);
1055
1056// Use macro to generate conditional function debug and display implementations
1057impl_conditional_function_debug_display!(ArcConditionalMutatingFunction<T, R>);