1use std::sync::Arc;
20
21#[derive(Clone, Debug)]
22pub struct StrRef {
23 parent: Arc<str>,
24 start: u32,
25 end: u32,
26}
27
28impl StrRef {
29 #[inline]
31 pub fn from_arc(parent: Arc<str>) -> Self {
32 let end = parent.len() as u32;
33 Self { parent, start: 0, end }
34 }
35
36 #[inline]
39 pub fn slice(parent: Arc<str>, start: usize, end: usize) -> Self {
40 debug_assert!(start <= end);
41 debug_assert!(end <= parent.len());
42 debug_assert!(parent.is_char_boundary(start));
43 debug_assert!(parent.is_char_boundary(end));
44 Self {
45 parent,
46 start: start as u32,
47 end: end as u32,
48 }
49 }
50
51 #[inline] pub fn as_str(&self) -> &str {
52 &self.parent[self.start as usize .. self.end as usize]
53 }
54
55 #[inline] pub fn len(&self) -> usize { (self.end - self.start) as usize }
56 #[inline] pub fn is_empty(&self) -> bool { self.end == self.start }
57
58 #[inline]
62 pub fn to_arc(&self) -> Arc<str> {
63 if self.start == 0 && self.end as usize == self.parent.len() {
64 Arc::clone(&self.parent)
65 } else {
66 Arc::<str>::from(self.as_str())
67 }
68 }
69}
70
71impl AsRef<str> for StrRef {
72 #[inline] fn as_ref(&self) -> &str { self.as_str() }
73}
74
75impl std::ops::Deref for StrRef {
76 type Target = str;
77 #[inline] fn deref(&self) -> &str { self.as_str() }
78}
79
80impl std::fmt::Display for StrRef {
81 #[inline] fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
82 f.write_str(self.as_str())
83 }
84}
85
86impl PartialEq for StrRef {
87 #[inline] fn eq(&self, other: &Self) -> bool { self.as_str() == other.as_str() }
88}
89impl Eq for StrRef {}
90
91impl PartialEq<str> for StrRef {
92 #[inline] fn eq(&self, other: &str) -> bool { self.as_str() == other }
93}
94impl PartialEq<&str> for StrRef {
95 #[inline] fn eq(&self, other: &&str) -> bool { self.as_str() == *other }
96}
97impl PartialEq<Arc<str>> for StrRef {
98 #[inline] fn eq(&self, other: &Arc<str>) -> bool { self.as_str() == other.as_ref() }
99}
100
101impl std::hash::Hash for StrRef {
102 #[inline] fn hash<H: std::hash::Hasher>(&self, state: &mut H) {
103 self.as_str().hash(state)
104 }
105}
106
107impl From<Arc<str>> for StrRef {
108 #[inline] fn from(a: Arc<str>) -> Self { Self::from_arc(a) }
109}
110impl From<&str> for StrRef {
111 #[inline] fn from(s: &str) -> Self { Self::from_arc(Arc::<str>::from(s)) }
112}
113impl From<String> for StrRef {
114 #[inline] fn from(s: String) -> Self { Self::from_arc(Arc::<str>::from(s)) }
115}