Rename StackString to InlineString to reflect the fact that it may not always be on the stack, rename modules
This commit is contained in:
1 parent
da09d5015b
commit
74e2bbf406
4 files changed
+57
-57
No files matched your search
File renamed without changes.
@@ -9,12 +9,12 @@ use std::{
|
|||||||
};
|
};
|
||||||
|
|
||||||
#[derive(Clone)]
|
#[derive(Clone)]
|
||||||
pub struct StackString<const N: usize> {
|
pub struct InlineString<const N: usize> {
|
||||||
buf: [u8; N],
|
buf: [u8; N],
|
||||||
len: u8,
|
len: u8,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> StackString<N> {
|
impl<const N: usize> InlineString<N> {
|
||||||
const MAX_LEN: u8 = {
|
const MAX_LEN: u8 = {
|
||||||
#[allow(clippy::cast_possible_truncation, clippy::checked_conversions)]
|
#[allow(clippy::cast_possible_truncation, clippy::checked_conversions)]
|
||||||
if N <= u8::MAX as usize {
|
if N <= u8::MAX as usize {
|
||||||
@@ -24,7 +24,7 @@ impl<const N: usize> StackString<N> {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
/// Creates a new `StackString` from a given byte buffer and length.
|
/// Creates a new `InlineString` from a given byte buffer and length.
|
||||||
///
|
///
|
||||||
/// # Safety
|
/// # Safety
|
||||||
///
|
///
|
||||||
@@ -35,7 +35,7 @@ impl<const N: usize> StackString<N> {
|
|||||||
Self { buf, len }
|
Self { buf, len }
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Returns a new empty `StackString`.
|
/// Returns a new empty `InlineString`.
|
||||||
#[inline]
|
#[inline]
|
||||||
#[must_use]
|
#[must_use]
|
||||||
pub const fn empty() -> Self {
|
pub const fn empty() -> Self {
|
||||||
@@ -46,7 +46,7 @@ impl<const N: usize> StackString<N> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn new<S>(s: &S) -> Result<Self, StackStringError>
|
pub fn new<S>(s: &S) -> Result<Self, InlineStringError>
|
||||||
where
|
where
|
||||||
S: AsRef<str> + ?Sized,
|
S: AsRef<str> + ?Sized,
|
||||||
{
|
{
|
||||||
@@ -55,11 +55,11 @@ impl<const N: usize> StackString<N> {
|
|||||||
let s = <S as AsRef<str>>::as_ref(s).as_bytes();
|
let s = <S as AsRef<str>>::as_ref(s).as_bytes();
|
||||||
|
|
||||||
// If the length of the string is greater than `Self::MAX_LEN`, it will not fit in the
|
// If the length of the string is greater than `Self::MAX_LEN`, it will not fit in the
|
||||||
// stack buffer so return `None`.
|
// buffer so return `None`.
|
||||||
let len = u8::try_from(s.len())
|
let len = u8::try_from(s.len())
|
||||||
.ok()
|
.ok()
|
||||||
.and_then(|len| (len <= Self::MAX_LEN).then_some(len))
|
.and_then(|len| (len <= Self::MAX_LEN).then_some(len))
|
||||||
.ok_or(StackStringError {
|
.ok_or(InlineStringError {
|
||||||
max_len: N,
|
max_len: N,
|
||||||
actual_len: s.len(),
|
actual_len: s.len(),
|
||||||
})?;
|
})?;
|
||||||
@@ -76,24 +76,24 @@ impl<const N: usize> StackString<N> {
|
|||||||
/// Returns a string slice pointing to the underlying string data.
|
/// Returns a string slice pointing to the underlying string data.
|
||||||
pub fn as_str(&self) -> &str {
|
pub fn as_str(&self) -> &str {
|
||||||
// SAFETY:
|
// SAFETY:
|
||||||
// `len` being less than or equal to `N` is an invariant of `StackString`, so it is
|
// `len` being less than or equal to `N` is an invariant of `InlineString`, so it is
|
||||||
// always within the bounds of `buf`.
|
// always within the bounds of `buf`.
|
||||||
let slice = unsafe { self.buf.get_unchecked(..usize::from(self.len)) };
|
let slice = unsafe { self.buf.get_unchecked(..usize::from(self.len)) };
|
||||||
|
|
||||||
// SAFETY:
|
// SAFETY:
|
||||||
// The first `len` bytes of `buf` being valid UTF-8 is an invariant of `StackString`.
|
// The first `len` bytes of `buf` being valid UTF-8 is an invariant of `InlineString`.
|
||||||
unsafe { str::from_utf8_unchecked(slice) }
|
unsafe { str::from_utf8_unchecked(slice) }
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Returns a mutable string slice pointing to the underlying string data.
|
/// Returns a mutable string slice pointing to the underlying string data.
|
||||||
pub fn as_str_mut(&mut self) -> &mut str {
|
pub fn as_str_mut(&mut self) -> &mut str {
|
||||||
// SAFETY:
|
// SAFETY:
|
||||||
// `len` being less than or equal to `N` is an invariant of `StackString`, so it is
|
// `len` being less than or equal to `N` is an invariant of `InlineString`, so it is
|
||||||
// always within the bounds of `buf`.
|
// always within the bounds of `buf`.
|
||||||
let slice = unsafe { self.buf.get_unchecked_mut(..usize::from(self.len)) };
|
let slice = unsafe { self.buf.get_unchecked_mut(..usize::from(self.len)) };
|
||||||
|
|
||||||
// SAFETY:
|
// SAFETY:
|
||||||
// The first `len` bytes of `buf` being valid UTF-8 is an invariant of `StackString`.
|
// The first `len` bytes of `buf` being valid UTF-8 is an invariant of `InlineString`.
|
||||||
unsafe { str::from_utf8_unchecked_mut(slice) }
|
unsafe { str::from_utf8_unchecked_mut(slice) }
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -110,14 +110,14 @@ impl<const N: usize> StackString<N> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> Default for StackString<N> {
|
impl<const N: usize> Default for InlineString<N> {
|
||||||
#[inline]
|
#[inline]
|
||||||
fn default() -> Self {
|
fn default() -> Self {
|
||||||
Self::empty()
|
Self::empty()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> ops::Deref for StackString<N> {
|
impl<const N: usize> ops::Deref for InlineString<N> {
|
||||||
type Target = str;
|
type Target = str;
|
||||||
|
|
||||||
#[inline]
|
#[inline]
|
||||||
@@ -126,43 +126,43 @@ impl<const N: usize> ops::Deref for StackString<N> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> ops::DerefMut for StackString<N> {
|
impl<const N: usize> ops::DerefMut for InlineString<N> {
|
||||||
#[inline]
|
#[inline]
|
||||||
fn deref_mut(&mut self) -> &mut Self::Target {
|
fn deref_mut(&mut self) -> &mut Self::Target {
|
||||||
self.as_str_mut()
|
self.as_str_mut()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> AsRef<str> for StackString<N> {
|
impl<const N: usize> AsRef<str> for InlineString<N> {
|
||||||
#[inline]
|
#[inline]
|
||||||
fn as_ref(&self) -> &str {
|
fn as_ref(&self) -> &str {
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> AsMut<str> for StackString<N> {
|
impl<const N: usize> AsMut<str> for InlineString<N> {
|
||||||
#[inline]
|
#[inline]
|
||||||
fn as_mut(&mut self) -> &mut str {
|
fn as_mut(&mut self) -> &mut str {
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> borrow::Borrow<str> for StackString<N> {
|
impl<const N: usize> borrow::Borrow<str> for InlineString<N> {
|
||||||
#[inline]
|
#[inline]
|
||||||
fn borrow(&self) -> &str {
|
fn borrow(&self) -> &str {
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> borrow::BorrowMut<str> for StackString<N> {
|
impl<const N: usize> borrow::BorrowMut<str> for InlineString<N> {
|
||||||
#[inline]
|
#[inline]
|
||||||
fn borrow_mut(&mut self) -> &mut str {
|
fn borrow_mut(&mut self) -> &mut str {
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, const N: usize> TryFrom<&'a str> for StackString<N> {
|
impl<'a, const N: usize> TryFrom<&'a str> for InlineString<N> {
|
||||||
type Error = StackStringError;
|
type Error = InlineStringError;
|
||||||
|
|
||||||
#[inline]
|
#[inline]
|
||||||
fn try_from(s: &'a str) -> Result<Self, Self::Error> {
|
fn try_from(s: &'a str) -> Result<Self, Self::Error> {
|
||||||
@@ -170,8 +170,8 @@ impl<'a, const N: usize> TryFrom<&'a str> for StackString<N> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> TryFrom<String> for StackString<N> {
|
impl<const N: usize> TryFrom<String> for InlineString<N> {
|
||||||
type Error = StackStringError;
|
type Error = InlineStringError;
|
||||||
|
|
||||||
#[inline]
|
#[inline]
|
||||||
fn try_from(s: String) -> Result<Self, Self::Error> {
|
fn try_from(s: String) -> Result<Self, Self::Error> {
|
||||||
@@ -179,8 +179,8 @@ impl<const N: usize> TryFrom<String> for StackString<N> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, const N: usize> TryFrom<Cow<'a, str>> for StackString<N> {
|
impl<'a, const N: usize> TryFrom<Cow<'a, str>> for InlineString<N> {
|
||||||
type Error = StackStringError;
|
type Error = InlineStringError;
|
||||||
|
|
||||||
#[inline]
|
#[inline]
|
||||||
fn try_from(s: Cow<'a, str>) -> Result<Self, Self::Error> {
|
fn try_from(s: Cow<'a, str>) -> Result<Self, Self::Error> {
|
||||||
@@ -188,45 +188,45 @@ impl<'a, const N: usize> TryFrom<Cow<'a, str>> for StackString<N> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> From<StackString<N>> for String {
|
impl<const N: usize> From<InlineString<N>> for String {
|
||||||
#[inline]
|
#[inline]
|
||||||
fn from(s: StackString<N>) -> Self {
|
fn from(s: InlineString<N>) -> Self {
|
||||||
s.into_string()
|
s.into_string()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize, const M: usize> PartialEq<StackString<M>> for StackString<N> {
|
impl<const N: usize, const M: usize> PartialEq<InlineString<M>> for InlineString<N> {
|
||||||
#[inline]
|
#[inline]
|
||||||
fn eq(&self, other: &StackString<M>) -> bool {
|
fn eq(&self, other: &InlineString<M>) -> bool {
|
||||||
**self == **other
|
**self == **other
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> Eq for StackString<N> {}
|
impl<const N: usize> Eq for InlineString<N> {}
|
||||||
|
|
||||||
impl<const N: usize, const M: usize> PartialOrd<StackString<M>> for StackString<N> {
|
impl<const N: usize, const M: usize> PartialOrd<InlineString<M>> for InlineString<N> {
|
||||||
#[inline]
|
#[inline]
|
||||||
fn partial_cmp(&self, other: &StackString<M>) -> Option<Ordering> {
|
fn partial_cmp(&self, other: &InlineString<M>) -> Option<Ordering> {
|
||||||
(**self).partial_cmp(&**other)
|
(**self).partial_cmp(&**other)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> Ord for StackString<N> {
|
impl<const N: usize> Ord for InlineString<N> {
|
||||||
#[inline]
|
#[inline]
|
||||||
fn cmp(&self, other: &Self) -> Ordering {
|
fn cmp(&self, other: &Self) -> Ordering {
|
||||||
(**self).cmp(&**other)
|
(**self).cmp(&**other)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> Hash for StackString<N> {
|
impl<const N: usize> Hash for InlineString<N> {
|
||||||
#[inline]
|
#[inline]
|
||||||
fn hash<H: Hasher>(&self, state: &mut H) {
|
fn hash<H: Hasher>(&self, state: &mut H) {
|
||||||
(**self).hash(state);
|
(**self).hash(state);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> str::FromStr for StackString<N> {
|
impl<const N: usize> str::FromStr for InlineString<N> {
|
||||||
type Err = StackStringError;
|
type Err = InlineStringError;
|
||||||
|
|
||||||
#[inline]
|
#[inline]
|
||||||
fn from_str(s: &str) -> Result<Self, Self::Err> {
|
fn from_str(s: &str) -> Result<Self, Self::Err> {
|
||||||
@@ -234,14 +234,14 @@ impl<const N: usize> str::FromStr for StackString<N> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> fmt::Debug for StackString<N> {
|
impl<const N: usize> fmt::Debug for InlineString<N> {
|
||||||
#[inline]
|
#[inline]
|
||||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||||
fmt::Debug::fmt(&**self, f)
|
fmt::Debug::fmt(&**self, f)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const N: usize> fmt::Display for StackString<N> {
|
impl<const N: usize> fmt::Display for InlineString<N> {
|
||||||
#[inline]
|
#[inline]
|
||||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||||
fmt::Display::fmt(&**self, f)
|
fmt::Display::fmt(&**self, f)
|
||||||
@@ -249,12 +249,12 @@ impl<const N: usize> fmt::Display for StackString<N> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct StackStringError {
|
pub struct InlineStringError {
|
||||||
max_len: usize,
|
max_len: usize,
|
||||||
actual_len: usize,
|
actual_len: usize,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl StackStringError {
|
impl InlineStringError {
|
||||||
pub fn max_len(&self) -> usize {
|
pub fn max_len(&self) -> usize {
|
||||||
self.max_len
|
self.max_len
|
||||||
}
|
}
|
||||||
@@ -264,15 +264,15 @@ impl StackStringError {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl fmt::Display for StackStringError {
|
impl fmt::Display for InlineStringError {
|
||||||
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
|
||||||
write!(
|
write!(
|
||||||
f,
|
f,
|
||||||
"string of length {} exceeds limit for `StackString<{}>`",
|
"string of length {} exceeds limit for `InlineString<{}>`",
|
||||||
self.actual_len,
|
self.actual_len,
|
||||||
self.max_len
|
self.max_len
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl error::Error for StackStringError {}
|
impl error::Error for InlineStringError {}
|
||||||
+4
-4
@@ -1,8 +1,8 @@
|
|||||||
pub mod experimental;
|
pub mod experimental;
|
||||||
pub mod fixed_string;
|
pub mod fixed;
|
||||||
pub mod stack_string;
|
pub mod inline;
|
||||||
pub mod shstring;
|
pub mod shstring;
|
||||||
|
|
||||||
pub use fixed_string::{FixedString, Error as FixedStringError};
|
pub use fixed::{FixedString, Error as FixedStringError};
|
||||||
pub use stack_string::StackString;
|
pub use inline::InlineString;
|
||||||
pub use shstring::{ShString, ShString22};
|
pub use shstring::{ShString, ShString22};
|
||||||
+11
-11
@@ -8,7 +8,7 @@ use std::{
|
|||||||
str::FromStr,
|
str::FromStr,
|
||||||
};
|
};
|
||||||
|
|
||||||
use super::StackString;
|
use super::InlineString;
|
||||||
|
|
||||||
/// A non-growable string where strings 22 bytes or shorter are stored on the stack and longer
|
/// A non-growable string where strings 22 bytes or shorter are stored on the stack and longer
|
||||||
/// strings are stored on the heap.
|
/// strings are stored on the heap.
|
||||||
@@ -35,7 +35,7 @@ impl<const N: usize> ShString<N> {
|
|||||||
#[inline]
|
#[inline]
|
||||||
#[must_use]
|
#[must_use]
|
||||||
pub const fn empty() -> Self {
|
pub const fn empty() -> Self {
|
||||||
Self(Repr::Stack(StackString::empty()))
|
Self(Repr::Inline(InlineString::empty()))
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Creates a new `ShString` from the given string slice, putting it on the stack if possible
|
/// Creates a new `ShString` from the given string slice, putting it on the stack if possible
|
||||||
@@ -47,8 +47,8 @@ impl<const N: usize> ShString<N> {
|
|||||||
S: AsRef<str>,
|
S: AsRef<str>,
|
||||||
Box<str>: From<S>,
|
Box<str>: From<S>,
|
||||||
{
|
{
|
||||||
match StackString::new(&s) {
|
match InlineString::new(&s) {
|
||||||
Ok(stack_buf) => Self(Repr::Stack(stack_buf)),
|
Ok(stack_buf) => Self(Repr::Inline(stack_buf)),
|
||||||
Err(_) => Self(Repr::Heap(Box::<str>::from(s))),
|
Err(_) => Self(Repr::Heap(Box::<str>::from(s))),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -58,7 +58,7 @@ impl<const N: usize> ShString<N> {
|
|||||||
#[must_use]
|
#[must_use]
|
||||||
pub fn as_str(&self) -> &str {
|
pub fn as_str(&self) -> &str {
|
||||||
match self {
|
match self {
|
||||||
Self(Repr::Stack(buf)) => buf,
|
Self(Repr::Inline(buf)) => buf,
|
||||||
Self(Repr::Heap(buf)) => buf,
|
Self(Repr::Heap(buf)) => buf,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -68,7 +68,7 @@ impl<const N: usize> ShString<N> {
|
|||||||
#[must_use]
|
#[must_use]
|
||||||
pub fn as_str_mut(&mut self) -> &mut str {
|
pub fn as_str_mut(&mut self) -> &mut str {
|
||||||
match self {
|
match self {
|
||||||
Self(Repr::Stack(buf)) => buf,
|
Self(Repr::Inline(buf)) => buf,
|
||||||
Self(Repr::Heap(buf)) => buf,
|
Self(Repr::Heap(buf)) => buf,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -78,7 +78,7 @@ impl<const N: usize> ShString<N> {
|
|||||||
#[must_use]
|
#[must_use]
|
||||||
pub fn into_string(self) -> String {
|
pub fn into_string(self) -> String {
|
||||||
match self {
|
match self {
|
||||||
Self(Repr::Stack(buf)) => buf.into_string(),
|
Self(Repr::Inline(buf)) => buf.into_string(),
|
||||||
Self(Repr::Heap(buf)) => buf.into_string(),
|
Self(Repr::Heap(buf)) => buf.into_string(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -94,7 +94,7 @@ impl<const N: usize> ShString<N> {
|
|||||||
#[must_use]
|
#[must_use]
|
||||||
pub fn len(&self) -> usize {
|
pub fn len(&self) -> usize {
|
||||||
match self {
|
match self {
|
||||||
Self(Repr::Stack(buf)) => buf.len(),
|
Self(Repr::Inline(buf)) => buf.len(),
|
||||||
Self(Repr::Heap(buf)) => buf.len(),
|
Self(Repr::Heap(buf)) => buf.len(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -113,7 +113,7 @@ impl<const N: usize> ShString<N> {
|
|||||||
#[must_use]
|
#[must_use]
|
||||||
pub fn is_empty(&self) -> bool {
|
pub fn is_empty(&self) -> bool {
|
||||||
match self {
|
match self {
|
||||||
Self(Repr::Stack(buf)) => buf.is_empty(),
|
Self(Repr::Inline(buf)) => buf.is_empty(),
|
||||||
Self(Repr::Heap(buf)) => buf.is_empty(),
|
Self(Repr::Heap(buf)) => buf.is_empty(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -132,7 +132,7 @@ impl<const N: usize> ShString<N> {
|
|||||||
#[must_use]
|
#[must_use]
|
||||||
pub fn heap_allocated(&self) -> bool {
|
pub fn heap_allocated(&self) -> bool {
|
||||||
match self {
|
match self {
|
||||||
Self(Repr::Stack(_)) => false,
|
Self(Repr::Inline(_)) => false,
|
||||||
Self(Repr::Heap(_)) => true,
|
Self(Repr::Heap(_)) => true,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -293,7 +293,7 @@ impl<'de, const N: usize> serde::Deserialize<'de> for ShString<N> {
|
|||||||
|
|
||||||
#[derive(Clone)]
|
#[derive(Clone)]
|
||||||
enum Repr<const N: usize> {
|
enum Repr<const N: usize> {
|
||||||
Stack(StackString<N>),
|
Inline(InlineString<N>),
|
||||||
Heap(Box<str>),
|
Heap(Box<str>),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in new issue
Block a user