Below I have a function that could work on the same data as source and destination, or different ones. If you pass no source, it should treat the destination as the source.
use core::ops::IndexMut;
use core::ops::Index;
use core::marker::PhantomData;
struct B<'a, T>{
_phantom: PhantomData<&'a T>
}
struct BMut<'a, T>{
_phantom: PhantomData<&'a mut T>
}
impl<'a, T> Index<T> for B<'a, T> {
type Output = T;
fn index(&self, t: T) -> &T {
unimplemented!()
}
}
impl<'a, T> Index<T> for BMut<'a, T> {
type Output = T;
fn index(&self, t: T) -> &T {
unimplemented!()
}
}
impl<'a, T> IndexMut<T> for BMut<'a, T> {
fn index_mut(&mut self, t: T) -> &mut T {
unimplemented!()
}
}
impl<'a, T> From<BMut<'a, T>> for B<'a, T> {
fn from(_e: BMut<'a, T>) -> Self {
B{
_phantom: PhantomData
}
}
}
trait A where Self: Sized {
fn transform(source: Option<&B<Self>>, destination: &mut BMut<Self>);
}
impl A for u64 {
fn transform(source: Option<&B<Self>>, destination: &mut BMut<Self>) {
let source = match source{
Some(source) => source,
None => destination.into()
};
//do a transformation here that reads and writes from destination.
//In case we specified a source, then it uses it, otherwise uses destination
//as a source. Technically this should be possible because it's impossible to pass
//a source that is equal to destination
}
}
The problem is that I cannot convert BMut to B. Yes, I could access BMut in the function a everytime I needed B if the source was not specified, but would be much cooler to have one type for source and be able to set it as destination only once.
⣿
Standard Error
error[E0277]: the trait bound `&B<'_, u64>: From<&mut BMut<'_, u64>>` is not satisfied
--> src/lib.rs:49:33
|
49 | None => destination.into()
| ^^^^ the trait `From<&mut BMut<'_, u64>>` is not implemented for `&B<'_, u64>`
|
= help: the following implementations were found:
<B<'a, T> as From<BMut<'a, T>>>
= note: required because of the requirements on the impl of `Into<&B<'_, u64>>` for `&mut BMut<'_, u64>`