chandra/core/
type_traits.rs

1use std::{collections::HashMap, fmt::Debug, marker::PhantomData};
2
3use super::{types::{Computable, Value}, operation::{Operation, OperationWrapper, Differentiable}, processor::Storage, allocated::{MemoryLayoutDescriptor, ParallelizationDescriptor}, operations::{var::Variable, call::Call, multiply::{Multiply, multiply}}};
4
5pub trait IndexAble: Clone + Debug {
6    type IndexResult;
7
8    fn index<O: Operation<u32>>(&self, index: O) -> Self::IndexResult;
9
10    fn get_reference(&self) -> String;
11
12    fn get_field() -> Option<String>;
13}
14
15pub trait GetAndSetable<R: Computable>: Clone + Debug {
16    fn get_variable(&self) -> Option<String>;
17}
18
19pub trait Iterable<R: Computable>: Operation<R> + Clone + Debug {
20    type StartOp: Operation<R>;
21    type NextOp: Operation<R>;
22    type BoundryOp: Operation<R>;
23
24    fn get_start(&self) -> Self::StartOp;
25    fn get_next(&self) -> Self::NextOp;
26    fn get_boundry(&self) -> Self::BoundryOp;
27}
28
29impl<R: Computable, O: Operation<R> + Iterable<R>> Iterable<R> for OperationWrapper<R, O> {
30    type StartOp = O::StartOp;
31
32    type NextOp = O::NextOp;
33
34    type BoundryOp = O::BoundryOp;
35
36    fn get_start(&self) -> Self::StartOp {
37        self.0.get_start()
38    }
39
40    fn get_next(&self) -> Self::NextOp {
41        self.0.get_next()
42    }
43
44    fn get_boundry(&self) -> Self::BoundryOp {
45        self.0.get_boundry()
46    }
47}
48
49pub trait ChandraFn {
50    type Result: Value;
51    type Inputs: FunctionInputs;
52    type FunctionScope: Operation<Self::Result>;
53}
54
55pub trait ChandraExtensionFn {
56    type Result: Value;
57    type Inputs: FunctionInputs;
58    type FunctionScope: Operation<Self::Result>;
59}
60
61pub trait FunctionInputs: Clone + Debug {}
62
63impl<R: Computable> FunctionInputs for (Variable<R>,) {}
64impl<R: Computable, R2: Computable> FunctionInputs for (Variable<R>, Variable<R2>) {}
65impl<R: Computable, R2: Computable, R3: Computable> FunctionInputs for (Variable<R>, Variable<R2>, Variable<R3>) {}
66impl<R: Computable, R2: Computable, R3: Computable, R4: Computable> FunctionInputs for (Variable<R>, Variable<R2>, Variable<R3>, Variable<R4>) {}
67impl<R: Computable, R2: Computable, R3: Computable, R4: Computable, R5: Computable> FunctionInputs for (Variable<R>, Variable<R2>, Variable<R3>, Variable<R4>, Variable<R5>) {}
68impl<R: Computable, R2: Computable, R3: Computable, R4: Computable, R5: Computable, R6: Computable> FunctionInputs for (Variable<R>, Variable<R2>, Variable<R3>, Variable<R4>, Variable<R5>, Variable<R6>) {}
69impl<R: Computable, R2: Computable, R3: Computable, R4: Computable, R5: Computable, R6: Computable, R7: Computable> FunctionInputs for (Variable<R>, Variable<R2>, Variable<R3>, Variable<R4>, Variable<R5>, Variable<R6>, Variable<R7>) {}
70impl<R: Computable, R2: Computable, R3: Computable, R4: Computable, R5: Computable, R6: Computable, R7: Computable, R8: Computable> FunctionInputs for (Variable<R>, Variable<R2>, Variable<R3>, Variable<R4>, Variable<R5>, Variable<R6>, Variable<R7>, Variable<R8>) {}
71
72
73pub trait CallInputs: Clone + Debug {}
74
75impl<R: Computable, O: Operation<R>> CallInputs for (OperationWrapper<R, O>,) {}
76impl<R: Computable, O: Operation<R>, R2: Computable, O2: Operation<R2>> CallInputs for (OperationWrapper<R, O>, OperationWrapper<R2, O2>) {}
77impl<R: Computable, O: Operation<R>, R2: Computable, O2: Operation<R2>, R3: Computable, O3: Operation<R3>> CallInputs for (OperationWrapper<R, O>, OperationWrapper<R2, O2>, OperationWrapper<R3, O3>) {}
78impl<R: Computable, O: Operation<R>, R2: Computable, O2: Operation<R2>, R3: Computable, O3: Operation<R3>, R4: Computable, O4: Operation<R4>> CallInputs for (OperationWrapper<R, O>, OperationWrapper<R2, O2>, OperationWrapper<R3, O3>,OperationWrapper<R4, O4>) {}
79impl<R: Computable, O: Operation<R>, R2: Computable, O2: Operation<R2>, R3: Computable, O3: Operation<R3>, R4: Computable, O4: Operation<R4>, R5: Computable, O5: Operation<R5>> CallInputs for (OperationWrapper<R, O>, OperationWrapper<R2, O2>, OperationWrapper<R3, O3>,OperationWrapper<R4, O4>, OperationWrapper<R5, O5>) {}
80impl<R: Computable, O: Operation<R>, R2: Computable, O2: Operation<R2>, R3: Computable, O3: Operation<R3>, R4: Computable, O4: Operation<R4>, R5: Computable, O5: Operation<R5>, R6: Computable, O6: Operation<R6>> CallInputs for (OperationWrapper<R, O>, OperationWrapper<R2, O2>, OperationWrapper<R3, O3>,OperationWrapper<R4, O4>, OperationWrapper<R5, O5>, OperationWrapper<R6, O6>) {}
81impl<R: Computable, O: Operation<R>, R2: Computable, O2: Operation<R2>, R3: Computable, O3: Operation<R3>, R4: Computable, O4: Operation<R4>, R5: Computable, O5: Operation<R5>, R6: Computable, O6: Operation<R6>, R7: Computable, O7: Operation<R7>> CallInputs for (OperationWrapper<R, O>, OperationWrapper<R2, O2>, OperationWrapper<R3, O3>,OperationWrapper<R4, O4>, OperationWrapper<R5, O5>, OperationWrapper<R6, O6>, OperationWrapper<R7, O7>) {}
82impl<R: Computable, O: Operation<R>, R2: Computable, O2: Operation<R2>, R3: Computable, O3: Operation<R3>, R4: Computable, O4: Operation<R4>, R5: Computable, O5: Operation<R5>, R6: Computable, O6: Operation<R6>, R7: Computable, O7: Operation<R7>, R8: Computable, O8: Operation<R8>> CallInputs for (OperationWrapper<R, O>, OperationWrapper<R2, O2>, OperationWrapper<R3, O3>,OperationWrapper<R4, O4>, OperationWrapper<R5, O5>, OperationWrapper<R6, O6>, OperationWrapper<R7, O7>, OperationWrapper<R8, O8>) {}
83
84
85pub trait CallMatchFunctionInputs<F: FunctionInputs>: Clone {}
86impl<R: Computable, O: Operation<R>> CallMatchFunctionInputs<(Variable<R>,)> for (OperationWrapper<R, O>,) {}
87impl<R: Computable, O: Operation<R>, R2: Computable, O2: Operation<R2>> CallMatchFunctionInputs<(Variable<R>, Variable<R2>)> for (OperationWrapper<R, O>, OperationWrapper<R2, O2>) {}
88impl<R: Computable, O: Operation<R>, R2: Computable, O2: Operation<R2>, R3: Computable, O3: Operation<R3>> CallMatchFunctionInputs<(Variable<R>, Variable<R2>, Variable<R3>)> for (OperationWrapper<R, O>, OperationWrapper<R2, O2>, OperationWrapper<R3, O3>) {}
89impl<R: Computable, O: Operation<R>, R2: Computable, O2: Operation<R2>, R3: Computable, O3: Operation<R3>, R4: Computable, O4: Operation<R4>> CallMatchFunctionInputs<(Variable<R>, Variable<R2>, Variable<R3>, Variable<R4>)> for (OperationWrapper<R, O>, OperationWrapper<R2, O2>, OperationWrapper<R3, O3>, OperationWrapper<R4, O4>) {}
90impl<R: Computable, O: Operation<R>, R2: Computable, O2: Operation<R2>, R3: Computable, O3: Operation<R3>, R4: Computable, O4: Operation<R4>, R5: Computable, O5: Operation<R5>> CallMatchFunctionInputs<(Variable<R>, Variable<R2>, Variable<R3>, Variable<R4>, Variable<R5>)> for (OperationWrapper<R, O>, OperationWrapper<R2, O2>, OperationWrapper<R3, O3>,OperationWrapper<R4, O4>, OperationWrapper<R5, O5>) {}
91impl<R: Computable, O: Operation<R>, R2: Computable, O2: Operation<R2>, R3: Computable, O3: Operation<R3>, R4: Computable, O4: Operation<R4>, R5: Computable, O5: Operation<R5>, R6: Computable, O6: Operation<R6>> CallMatchFunctionInputs<(Variable<R>, Variable<R2>, Variable<R3>, Variable<R4>, Variable<R5>, Variable<R6>)> for (OperationWrapper<R, O>, OperationWrapper<R2, O2>, OperationWrapper<R3, O3>,OperationWrapper<R4, O4>, OperationWrapper<R5, O5>, OperationWrapper<R6, O6>) {}
92impl<R: Computable, O: Operation<R>, R2: Computable, O2: Operation<R2>, R3: Computable, O3: Operation<R3>, R4: Computable, O4: Operation<R4>, R5: Computable, O5: Operation<R5>, R6: Computable, O6: Operation<R6>, R7: Computable, O7: Operation<R7>> CallMatchFunctionInputs<(Variable<R>, Variable<R2>, Variable<R3>, Variable<R4>, Variable<R5>, Variable<R6>, Variable<R7>)> for (OperationWrapper<R, O>, OperationWrapper<R2, O2>, OperationWrapper<R3, O3>,OperationWrapper<R4, O4>, OperationWrapper<R5, O5>, OperationWrapper<R6, O6>, OperationWrapper<R7, O7>) {}
93impl<R: Computable, O: Operation<R>, R2: Computable, O2: Operation<R2>, R3: Computable, O3: Operation<R3>, R4: Computable, O4: Operation<R4>, R5: Computable, O5: Operation<R5>, R6: Computable, O6: Operation<R6>, R7: Computable, O7: Operation<R7>, R8: Computable, O8: Operation<R8>> CallMatchFunctionInputs<(Variable<R>, Variable<R2>, Variable<R3>, Variable<R4>, Variable<R5>, Variable<R6>, Variable<R7>, Variable<R8>)> for (OperationWrapper<R, O>, OperationWrapper<R2, O2>, OperationWrapper<R3, O3>,OperationWrapper<R4, O4>, OperationWrapper<R5, O5>, OperationWrapper<R6, O6>, OperationWrapper<R7, O7>, OperationWrapper<R8, O8>) {}
94
95pub trait DiffableFunctionInputs<R: Computable, F: FunctionInputs>: CallInputs + CallMatchFunctionInputs<F> {
96    type Diff<OF: Differentiable<R>>: Operation<R>;
97
98    fn contains_var<RV: Clone>(&self, var: Variable<RV>) -> bool;
99    fn map_variable<RV: Clone>(&self, var: Variable<RV>, f_inputs: F) -> Option<Variable<RV>>;
100    fn auto_diff_for<RV: Clone, O: Differentiable<R>>(&self, call: Call<R, F, Self, O>, var: Variable<RV>, og: Variable<RV>, var_trace: &mut HashMap<String, Vec<String>>) -> Self::Diff<O>;
101}
102
103impl<R: Calculatable, O: Differentiable<R>> DiffableFunctionInputs<R, (Variable<R>,)> for (OperationWrapper<R, O>,) {
104    type Diff<OF: Differentiable<R>> = OperationWrapper<R, Multiply<R, Call<R, (Variable<R>,), Self, OF::Diff>, OperationWrapper<R, O::Diff>>>;
105
106    fn contains_var<RV: Clone>(&self, var: Variable<RV>) -> bool {
107        self.0.contains_var(var)
108    }
109
110    fn map_variable<RV: Clone>(&self, var: Variable<RV>, f_inputs: (Variable<R>,)) -> Option<Variable<RV>> {
111        if self.0.contains_var(var.clone()) {
112            let mut result = var;
113            result.reference = f_inputs.0.reference.clone();
114            Some(result)
115        } else {
116            None
117        }
118    }
119
120    fn auto_diff_for<RV: Clone, OF: Differentiable<R>>(&self, call: Call<R, (Variable<R>,), Self, OF>, var: Variable<RV>, og: Variable<RV>, var_trace: &mut HashMap<String, Vec<String>>) -> Self::Diff<OF> {
121        multiply(Call { inputs: self.clone(), function: call.function.auto_diff_for(var.clone(), var_trace) }, OperationWrapper(self.0.0.auto_diff_for(og, var_trace), PhantomData)) //(OperationWrapper(self.0.0.auto_diff_for(var, var_trace), PhantomData),)
122    }
123}
124
125impl<R: Calculatable, O: Differentiable<R>, O2: Differentiable<R>> DiffableFunctionInputs<R, (Variable<R>, Variable<R>)> for (OperationWrapper<R, O>, OperationWrapper<R, O2>) {
126    type Diff<OF: Differentiable<R>> = OperationWrapper<R, Multiply<R, Call<R, (Variable<R>, Variable<R>), Self, OF::Diff>, OperationWrapper<R, Multiply<R, OperationWrapper<R, O::Diff>, OperationWrapper<R, O2::Diff>>>>>;
127
128    fn contains_var<RV: Clone>(&self, var: Variable<RV>) -> bool {
129        self.0.contains_var(var.clone()) || self.1.contains_var(var)
130    }
131
132    fn map_variable<RV: Clone>(&self, var: Variable<RV>, f_inputs: (Variable<R>, Variable<R>)) -> Option<Variable<RV>> {
133        if self.0.contains_var(var.clone()) {
134            let mut result = var;
135            result.reference = f_inputs.0.reference.clone();
136            Some(result)
137        } else if self.1.contains_var(var.clone()) {
138            let mut result = var;
139            result.reference = f_inputs.1.reference.clone();
140            Some(result)
141        } else {
142            None
143        }
144    }
145
146    fn auto_diff_for<RV: Clone, OF: Differentiable<R>>(&self, call: Call<R, (Variable<R>, Variable<R>), Self, OF>, var: Variable<RV>, og: Variable<RV>, var_trace: &mut HashMap<String, Vec<String>>) -> Self::Diff<OF> {
147        multiply(Call { inputs: self.clone(), function: call.function.auto_diff_for(var.clone(), var_trace) }, multiply(OperationWrapper(self.0.0.auto_diff_for(og.clone(), var_trace), PhantomData), OperationWrapper(self.1.0.auto_diff_for(og, var_trace), PhantomData))) 
148    }
149
150}
151
152
153pub trait Generalizable: Clone + Send + Sync {
154    fn get_memory_layout() -> MemoryLayoutDescriptor;
155
156    fn get_parallelization_info(&self) -> ParallelizationDescriptor;
157}
158
159
160
161pub trait FromMut<T> {
162    type Result<'a>: Clone + Send + Sync where T: 'a;
163    fn from_mut<'a>(value: &'a mut T) -> Self::Result<'_>;
164}
165
166impl<T: Clone + Send + Sync> FromMut<T> for T {
167    type Result<'a> = T where T: 'a;
168
169    fn from_mut<'a>(value: &'a mut T) -> Self::Result<'_> {
170        value.clone()
171    }
172}
173
174pub trait MemoryMapable<S: Storage>: Generalizable + 'static {
175    type Mapped<'a>: FromMut<S::MappedType<Self>> + Clone;
176
177    fn get_struct_map(&self) -> HashMap<String, String>;
178
179    fn to_memory_bytes(&self) -> Vec<u8>;
180    fn from_memory_bytes(bytes: Vec<u8>) -> Self;
181    fn into_processor_mapped(self) -> S::MappedType<Self>;
182}
183
184pub trait Calculatable: Computable + ::core::ops::Add<Self, Output = Self> + ::core::ops::Sub<Self, Output = Self> + ::core::ops::Mul<Self, Output = Self>  + std::cmp::PartialOrd + ::core::ops::Div<Self, Output = Self> {}
185
186impl<C: Computable> Calculatable for C where C: ::core::ops::Add<C, Output = C> + ::core::ops::Sub<C, Output = C> + ::core::ops::Mul<C, Output = C> + std::cmp::PartialOrd + ::core::ops::Div<C, Output = C> {
187
188}