Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 4 additions & 4 deletions .github/workflows/ci_check.yml
Original file line number Diff line number Diff line change
Expand Up @@ -10,12 +10,12 @@ jobs:
ci_check:
runs-on: 'ubuntu-latest'
steps:
- uses: 'actions/checkout@v2'
- uses: 'actions/setup-java@v3'
- uses: 'actions/checkout@v4'
- uses: 'actions/setup-java@v4'
with:
distribution: 'liberica'
java-version: '20'
- uses: 'actions/cache@v2'
- uses: 'actions/cache@v4'
with:
path: |
~/.rustup/toolchains
Expand Down Expand Up @@ -114,4 +114,4 @@ jobs:
- name: 'check toad-string'
run: 'cargo make ci'
if: github.ref == 'refs/heads/main' || steps.package_changed.outputs.toad-string == 'true'
working-directory: 'toad-map'
working-directory: 'toad-string'
10 changes: 5 additions & 5 deletions .github/workflows/release-please.yml
Original file line number Diff line number Diff line change
Expand Up @@ -10,17 +10,17 @@ jobs:

runs-on: ubuntu-latest
steps:
- uses: google-github-actions/release-please-action@v3
- uses: google-github-actions/release-please-action@v4
id: release
with:
token: ${{secrets.RELEASE_PLEASE_GITHUB_TOKEN}}
sequential-calls: true
command: manifest
config-file: release-please-config.json
manifest-file: .release-please-manifest.json

- uses: actions/checkout@v2
- uses: actions/checkout@v4
if: ${{ steps.release.outputs.releases_created }}

- uses: actions/cache@v2
- uses: actions/cache@v4
if: ${{ steps.release.outputs.releases_created }}
with:
path: |
Expand Down
60 changes: 40 additions & 20 deletions toad-array/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,8 @@ use toad_len::Len;

/// Operations on ordered indexed collections
pub trait Indexed<T>
where Self: Len + Deref<Target = [T]>
where
Self: Len + Deref<Target = [T]>,
{
/// Insert a new element at `ix`, shifting all other elements to the right.
///
Expand Down Expand Up @@ -181,7 +182,8 @@ pub trait Indexed<T>
/// assert_eq!(v, vec![5]);
/// ```
fn drop_while<F>(&mut self, f: F)
where F: for<'a> Fn(&'a T) -> bool
where
F: for<'a> Fn(&'a T) -> bool,
{
match self.get(0) {
| Some(t) if !f(&t) => return,
Expand All @@ -200,7 +202,8 @@ pub trait Indexed<T>
/// - `Vec` is `Reserve`, and invokes `Vec::with_capacity`
/// - `tinyvec::ArrayVec` is `Reserve` and invokes `Default::default()` because creating an `ArrayVec` automatically allocates the required space on the stack.
pub trait Reserve
where Self: Default
where
Self: Default,
{
/// Create an instance of the collection with a given capacity.
///
Expand All @@ -218,7 +221,8 @@ pub trait Reserve
///
/// If self was longer, drops elements up to `len`
pub trait Trunc
where Self: Sized
where
Self: Sized,
{
#[allow(missing_docs)]
fn trunc(&mut self, len: usize) -> ();
Expand All @@ -236,7 +240,9 @@ impl<T> Trunc for Vec<T> {
}
}

impl<T, const N: usize> Trunc for tinyvec::ArrayVec<[T; N]> where T: Default
impl<T, const N: usize> Trunc for tinyvec::ArrayVec<[T; N]>
where
T: Default,
{
fn trunc(&mut self, len: usize) -> () {
self.truncate(len)
Expand All @@ -251,21 +257,24 @@ impl<T, const N: usize> Trunc for tinyvec::ArrayVec<[T; N]> where T: Default
pub trait Filled<T>: Sized {
#[allow(missing_docs)]
fn filled(t: T) -> Option<Self>
where T: Copy
where
T: Copy,
{
Self::filled_using(|| t)
}

#[allow(missing_docs)]
fn filled_default() -> Option<Self>
where T: Default
where
T: Default,
{
Self::filled_using(|| Default::default())
}

#[allow(missing_docs)]
fn filled_using<F>(f: F) -> Option<Self>
where F: Fn() -> T;
where
F: Fn() -> T;
}

#[cfg(feature = "alloc")]
Expand All @@ -278,24 +287,29 @@ impl<T> Reserve for Vec<T> {
#[cfg(feature = "alloc")]
impl<T> Filled<T> for Vec<T> {
fn filled_using<F>(_: F) -> Option<Self>
where F: Fn() -> T
where
F: Fn() -> T,
{
None
}
}

impl<A: tinyvec::Array> Reserve for tinyvec::ArrayVec<A> {}

impl<T, const N: usize> Filled<T> for tinyvec::ArrayVec<[T; N]> where T: Default
impl<T, const N: usize> Filled<T> for tinyvec::ArrayVec<[T; N]>
where
T: Default,
{
fn filled_using<F>(f: F) -> Option<Self>
where F: Fn() -> T
where
F: Fn() -> T,
{
Some(core::iter::repeat(()).take(N).map(|_| f()).collect())
}

fn filled(t: T) -> Option<Self>
where T: Copy
where
T: Copy,
{
Some(Self::from([t; N]))
}
Expand Down Expand Up @@ -347,7 +361,8 @@ pub trait Array:

/// Collections that support extending themselves mutably from copyable slices
pub trait AppendCopy<T>
where T: Copy
where
T: Copy,
{
/// Extend self mutably, copying from a slice.
///
Expand All @@ -360,16 +375,19 @@ pub trait AppendCopy<T>
}

#[cfg(feature = "alloc")]
impl<T> AppendCopy<T> for Vec<T> where T: Copy
impl<T> AppendCopy<T> for Vec<T>
where
T: Copy,
{
fn append_copy(&mut self, i: &[T]) {
self.extend(i);
}
}

impl<T, A> AppendCopy<T> for tinyvec::ArrayVec<A>
where T: Copy,
A: tinyvec::Array<Item = T>
where
T: Copy,
A: tinyvec::Array<Item = T>,
{
fn append_copy(&mut self, i: &[T]) {
self.extend_from_slice(i);
Expand Down Expand Up @@ -397,15 +415,17 @@ impl<T> Indexed<T> for Vec<T> {
}

impl<A, T> Array for tinyvec::ArrayVec<A>
where Self: Filled<T> + Trunc,
A: tinyvec::Array<Item = T>
where
Self: Filled<T> + Trunc,
A: tinyvec::Array<Item = T>,
{
type Item = T;
}

impl<A> Indexed<A::Item> for tinyvec::ArrayVec<A>
where Self: Filled<A::Item> + Trunc,
A: tinyvec::Array
where
Self: Filled<A::Item> + Trunc,
A: tinyvec::Array,
{
fn insert(&mut self, ix: usize, t: A::Item) {
tinyvec::ArrayVec::insert(self, ix, t)
Expand Down
33 changes: 23 additions & 10 deletions toad-common/src/array.rs
Original file line number Diff line number Diff line change
Expand Up @@ -103,7 +103,8 @@ pub trait Reserve: Default {
///
/// If self was longer, drops elements up to `len`
pub trait Trunc
where Self: Sized
where
Self: Sized,
{
#[allow(missing_docs)]
fn trunc(&mut self, len: usize) -> ();
Expand All @@ -121,7 +122,9 @@ impl<T> Trunc for Vec<T> {
}
}

impl<T, const N: usize> Trunc for tinyvec::ArrayVec<[T; N]> where T: Default
impl<T, const N: usize> Trunc for tinyvec::ArrayVec<[T; N]>
where
T: Default,
{
fn trunc(&mut self, len: usize) -> () {
self.truncate(len)
Expand All @@ -136,21 +139,24 @@ impl<T, const N: usize> Trunc for tinyvec::ArrayVec<[T; N]> where T: Default
pub trait Filled<T>: Sized {
#[allow(missing_docs)]
fn filled(t: T) -> Option<Self>
where T: Copy
where
T: Copy,
{
Self::filled_using(|| t)
}

#[allow(missing_docs)]
fn filled_default() -> Option<Self>
where T: Default
where
T: Default,
{
Self::filled_using(|| Default::default())
}

#[allow(missing_docs)]
fn filled_using<F>(f: F) -> Option<Self>
where F: Fn() -> T;
where
F: Fn() -> T;
}

#[cfg(feature = "alloc")]
Expand All @@ -163,24 +169,29 @@ impl<T> Reserve for Vec<T> {
#[cfg(feature = "alloc")]
impl<T> Filled<T> for Vec<T> {
fn filled_using<F>(_: F) -> Option<Self>
where F: Fn() -> T
where
F: Fn() -> T,
{
None
}
}

impl<A: tinyvec::Array> Reserve for tinyvec::ArrayVec<A> {}

impl<T, const N: usize> Filled<T> for tinyvec::ArrayVec<[T; N]> where T: Default
impl<T, const N: usize> Filled<T> for tinyvec::ArrayVec<[T; N]>
where
T: Default,
{
fn filled_using<F>(f: F) -> Option<Self>
where F: Fn() -> T
where
F: Fn() -> T,
{
Some(core::iter::repeat(()).take(N).map(|_| f()).collect())
}

fn filled(t: T) -> Option<Self>
where T: Copy
where
T: Copy,
{
Some(Self::from([t; N]))
}
Expand Down Expand Up @@ -282,7 +293,9 @@ impl<T> Array for Vec<T> {
}
}

impl<A: tinyvec::Array<Item = T>, T> Array for tinyvec::ArrayVec<A> where Self: Filled<T> + Trunc
impl<A: tinyvec::Array<Item = T>, T> Array for tinyvec::ArrayVec<A>
where
Self: Filled<T> + Trunc,
{
type Item = T;

Expand Down
51 changes: 25 additions & 26 deletions toad-common/src/cursor.rs
Original file line number Diff line number Diff line change
Expand Up @@ -73,25 +73,22 @@ impl<T: AsRef<[u8]>> Cursor<T> {
#[allow(clippy::should_implement_trait)]
pub fn next(&mut self) -> Option<u8> {
self.take_exact(1).and_then(|a| match a {
| &[a] => Some(a),
| _ => None,
})
| &[a] => Some(a),
| _ => None,
})
}

/// Take `n` bytes from the cursor, stopping early if
/// the end of the buffer is encountered.
///
/// Runs in O(1) time.
pub fn take(&mut self, n: usize) -> &[u8] {
Self::peek_(self.len, self.cursor, &self.t, n).map(|a| {
Self::skip_(&mut self.cursor, self.len, n);
a
})
.unwrap_or_else(|| {
Self::take_until_end_(&mut self.cursor,
self.len,
&self.t)
})
Self::peek_(self.len, self.cursor, &self.t, n)
.map(|a| {
Self::skip_(&mut self.cursor, self.len, n);
a
})
.unwrap_or_else(|| Self::take_until_end_(&mut self.cursor, self.len, &self.t))
}

/// Take `n` bytes from the cursor, returning None if
Expand All @@ -100,9 +97,9 @@ impl<T: AsRef<[u8]>> Cursor<T> {
/// Runs in O(1) time.
pub fn take_exact(&mut self, n: usize) -> Option<&[u8]> {
Self::peek_(self.len, self.cursor, &self.t, n).map(|a| {
Self::skip_(&mut self.cursor, self.len, n);
a
})
Self::skip_(&mut self.cursor, self.len, n);
a
})
}

/// Without advancing the position, look at the next
Expand Down Expand Up @@ -143,15 +140,16 @@ impl<T: AsRef<[u8]>> Cursor<T> {
return &[];
}

(self.cursor..self.len).into_iter()
.take_while(|ix| f(self.t.as_ref()[*ix]))
.last()
.map(|end_ix| {
let out = &self.t.as_ref()[self.cursor..=end_ix];
self.cursor = end_ix + 1;
out
})
.unwrap_or(&[])
(self.cursor..self.len)
.into_iter()
.take_while(|ix| f(self.t.as_ref()[*ix]))
.last()
.map(|end_ix| {
let out = &self.t.as_ref()[self.cursor..=end_ix];
self.cursor = end_ix + 1;
out
})
.unwrap_or(&[])
}

/// Whether the cursor has reached the end
Expand Down Expand Up @@ -269,8 +267,9 @@ mod tests {
#[test]
pub fn take_while() {
let til_slash = |c: &mut Cursor<&str>| {
core::str::from_utf8(c.take_while(|b| (b as char) != '/')).unwrap()
.to_string()
core::str::from_utf8(c.take_while(|b| (b as char) != '/'))
.unwrap()
.to_string()
};

let mut cur = Cursor::new("abc/def");
Expand Down
Loading
Loading