structural_typing/
access.rs1use core::marker::PhantomData;
3
4use crate::presence::InferPresence;
5
6pub trait Access<T>: InferPresence<T> {
8 const IS_ABSENT: bool;
10
11 type RemainderFrom<Source: Access<T>>: Access<T>;
13
14 fn get(&self) -> Option<&T>;
16 fn get_mut(&mut self) -> Option<&mut T>;
18 fn into_option(self) -> Option<T>;
20
21 fn from_value(value: T) -> (Self, Self::RemainderFrom<T>)
23 where
24 Self: Sized;
25
26 #[allow(clippy::type_complexity)]
32 fn try_from_option(
33 value: Option<T>,
34 ) -> Result<(Self, Self::RemainderFrom<Option<T>>), Option<T>>
35 where
36 Self: Sized;
37}
38
39pub fn is_absent<A: Access<T>, T>(_value: &A) -> bool {
41 A::IS_ABSENT
42}
43
44impl<T> Access<T> for PhantomData<T> {
45 const IS_ABSENT: bool = true;
46
47 type RemainderFrom<Source: Access<T>> = Source;
48
49 #[inline]
50 fn get(&self) -> Option<&T> {
51 None
52 }
53 #[inline]
54 fn get_mut(&mut self) -> Option<&mut T> {
55 None
56 }
57 #[inline]
58 fn into_option(self) -> Option<T> {
59 None
60 }
61
62 #[inline]
63 fn from_value(value: T) -> (Self, Self::RemainderFrom<T>) {
64 (PhantomData, value)
65 }
66
67 #[inline]
68 fn try_from_option(
69 value: Option<T>,
70 ) -> Result<(Self, Self::RemainderFrom<Option<T>>), Option<T>> {
71 Ok((PhantomData, value))
72 }
73}
74
75impl<T: Sized> Access<T> for T {
76 const IS_ABSENT: bool = false;
77
78 type RemainderFrom<Source: Access<T>> = PhantomData<T>;
79
80 #[inline]
81 fn get(&self) -> Option<&T> {
82 Some(self)
83 }
84 #[inline]
85 fn get_mut(&mut self) -> Option<&mut T> {
86 Some(self)
87 }
88 #[inline]
89 fn into_option(self) -> Option<T> {
90 Some(self)
91 }
92
93 #[inline]
94 fn from_value(value: T) -> (Self, Self::RemainderFrom<T>) {
95 (value, PhantomData)
96 }
97
98 #[inline]
99 fn try_from_option(
100 value: Option<T>,
101 ) -> Result<(Self, Self::RemainderFrom<Option<T>>), Option<T>> {
102 match value {
103 Some(v) => Ok((v, PhantomData)),
104 None => Err(None),
105 }
106 }
107}
108
109impl<T> Access<T> for Option<T> {
110 const IS_ABSENT: bool = false;
111
112 type RemainderFrom<Source: Access<T>> = PhantomData<T>;
113
114 #[inline]
115 fn get(&self) -> Option<&T> {
116 self.as_ref()
117 }
118 #[inline]
119 fn get_mut(&mut self) -> Option<&mut T> {
120 self.as_mut()
121 }
122 #[inline]
123 fn into_option(self) -> Option<T> {
124 self
125 }
126
127 #[inline]
128 fn from_value(value: T) -> (Self, Self::RemainderFrom<T>) {
129 (Some(value), PhantomData)
130 }
131
132 #[inline]
133 fn try_from_option(
134 value: Option<T>,
135 ) -> Result<(Self, Self::RemainderFrom<Option<T>>), Option<T>> {
136 Ok((value, PhantomData))
137 }
138}