mirror of
https://github.com/RGBCube/cstree
synced 2025-07-27 17:17:45 +00:00
refactor green tree iterators into own module
This commit is contained in:
parent
2aaf4169da
commit
3982732d42
5 changed files with 101 additions and 95 deletions
|
@ -5,6 +5,7 @@
|
||||||
mod builder;
|
mod builder;
|
||||||
mod element;
|
mod element;
|
||||||
mod interner;
|
mod interner;
|
||||||
|
mod iter;
|
||||||
mod node;
|
mod node;
|
||||||
mod token;
|
mod token;
|
||||||
|
|
||||||
|
@ -14,7 +15,8 @@ use self::element::{GreenElement, PackedGreenElement};
|
||||||
pub use self::{
|
pub use self::{
|
||||||
builder::{Checkpoint, GreenNodeBuilder, NodeCache},
|
builder::{Checkpoint, GreenNodeBuilder, NodeCache},
|
||||||
interner::TokenInterner,
|
interner::TokenInterner,
|
||||||
node::{Children, GreenNode},
|
iter::GreenNodeChildren,
|
||||||
|
node::GreenNode,
|
||||||
token::GreenToken,
|
token::GreenToken,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
92
src/green/iter.rs
Normal file
92
src/green/iter.rs
Normal file
|
@ -0,0 +1,92 @@
|
||||||
|
//! Green tree iterators.
|
||||||
|
|
||||||
|
use std::{iter::FusedIterator, slice};
|
||||||
|
|
||||||
|
use super::{element::PackedGreenElement, GreenElementRef};
|
||||||
|
|
||||||
|
/// An iterator over a [`GreenNode`](crate::GreenNode)'s children.
|
||||||
|
#[derive(Debug, Clone)]
|
||||||
|
pub struct GreenNodeChildren<'a> {
|
||||||
|
pub(super) inner: slice::Iter<'a, PackedGreenElement>,
|
||||||
|
}
|
||||||
|
|
||||||
|
// NB: forward everything stable that iter::Slice specializes as of Rust 1.39.0
|
||||||
|
impl ExactSizeIterator for GreenNodeChildren<'_> {
|
||||||
|
#[inline(always)]
|
||||||
|
fn len(&self) -> usize {
|
||||||
|
self.inner.len()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> Iterator for GreenNodeChildren<'a> {
|
||||||
|
type Item = GreenElementRef<'a>;
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
fn next(&mut self) -> Option<GreenElementRef<'a>> {
|
||||||
|
self.inner.next().map(PackedGreenElement::as_ref)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
fn size_hint(&self) -> (usize, Option<usize>) {
|
||||||
|
self.inner.size_hint()
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
fn count(self) -> usize
|
||||||
|
where
|
||||||
|
Self: Sized,
|
||||||
|
{
|
||||||
|
self.inner.count()
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
fn nth(&mut self, n: usize) -> Option<Self::Item> {
|
||||||
|
self.inner.nth(n).map(PackedGreenElement::as_ref)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
fn last(mut self) -> Option<Self::Item>
|
||||||
|
where
|
||||||
|
Self: Sized,
|
||||||
|
{
|
||||||
|
self.next_back()
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
fn fold<Acc, Fold>(self, init: Acc, mut f: Fold) -> Acc
|
||||||
|
where
|
||||||
|
Fold: FnMut(Acc, Self::Item) -> Acc,
|
||||||
|
{
|
||||||
|
let mut accum = init;
|
||||||
|
for x in self {
|
||||||
|
accum = f(accum, x);
|
||||||
|
}
|
||||||
|
accum
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<'a> DoubleEndedIterator for GreenNodeChildren<'a> {
|
||||||
|
#[inline]
|
||||||
|
fn next_back(&mut self) -> Option<Self::Item> {
|
||||||
|
self.inner.next_back().map(PackedGreenElement::as_ref)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
fn nth_back(&mut self, n: usize) -> Option<Self::Item> {
|
||||||
|
self.inner.nth_back(n).map(PackedGreenElement::as_ref)
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
fn rfold<Acc, Fold>(mut self, init: Acc, mut f: Fold) -> Acc
|
||||||
|
where
|
||||||
|
Fold: FnMut(Acc, Self::Item) -> Acc,
|
||||||
|
{
|
||||||
|
let mut accum = init;
|
||||||
|
while let Some(x) = self.next_back() {
|
||||||
|
accum = f(accum, x);
|
||||||
|
}
|
||||||
|
accum
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl FusedIterator for GreenNodeChildren<'_> {}
|
|
@ -1,13 +1,12 @@
|
||||||
use std::{
|
use std::{
|
||||||
hash::{Hash, Hasher},
|
hash::{Hash, Hasher},
|
||||||
iter::FusedIterator,
|
|
||||||
slice,
|
slice,
|
||||||
};
|
};
|
||||||
|
|
||||||
use fxhash::FxHasher32;
|
use fxhash::FxHasher32;
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
green::{GreenElement, GreenElementRef, PackedGreenElement, SyntaxKind},
|
green::{iter::GreenNodeChildren, GreenElement, PackedGreenElement, SyntaxKind},
|
||||||
TextSize,
|
TextSize,
|
||||||
};
|
};
|
||||||
use triomphe::{Arc, HeaderWithLength, ThinArc};
|
use triomphe::{Arc, HeaderWithLength, ThinArc};
|
||||||
|
@ -135,8 +134,8 @@ impl GreenNode {
|
||||||
|
|
||||||
/// Iterator over all children of this node.
|
/// Iterator over all children of this node.
|
||||||
#[inline]
|
#[inline]
|
||||||
pub fn children(&self) -> Children<'_> {
|
pub fn children(&self) -> GreenNodeChildren<'_> {
|
||||||
Children {
|
GreenNodeChildren {
|
||||||
inner: self.data.slice.iter(),
|
inner: self.data.slice.iter(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -156,90 +155,3 @@ impl PartialEq for GreenNode {
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Eq for GreenNode {}
|
impl Eq for GreenNode {}
|
||||||
|
|
||||||
/// An iterator over a [`GreenNode`]'s children.
|
|
||||||
#[derive(Debug, Clone)]
|
|
||||||
pub struct Children<'a> {
|
|
||||||
inner: slice::Iter<'a, PackedGreenElement>,
|
|
||||||
}
|
|
||||||
|
|
||||||
// NB: forward everything stable that iter::Slice specializes as of Rust 1.39.0
|
|
||||||
impl ExactSizeIterator for Children<'_> {
|
|
||||||
#[inline(always)]
|
|
||||||
fn len(&self) -> usize {
|
|
||||||
self.inner.len()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<'a> Iterator for Children<'a> {
|
|
||||||
type Item = GreenElementRef<'a>;
|
|
||||||
|
|
||||||
#[inline]
|
|
||||||
fn next(&mut self) -> Option<GreenElementRef<'a>> {
|
|
||||||
self.inner.next().map(PackedGreenElement::as_ref)
|
|
||||||
}
|
|
||||||
|
|
||||||
#[inline]
|
|
||||||
fn size_hint(&self) -> (usize, Option<usize>) {
|
|
||||||
self.inner.size_hint()
|
|
||||||
}
|
|
||||||
|
|
||||||
#[inline]
|
|
||||||
fn count(self) -> usize
|
|
||||||
where
|
|
||||||
Self: Sized,
|
|
||||||
{
|
|
||||||
self.inner.count()
|
|
||||||
}
|
|
||||||
|
|
||||||
#[inline]
|
|
||||||
fn nth(&mut self, n: usize) -> Option<Self::Item> {
|
|
||||||
self.inner.nth(n).map(PackedGreenElement::as_ref)
|
|
||||||
}
|
|
||||||
|
|
||||||
#[inline]
|
|
||||||
fn last(mut self) -> Option<Self::Item>
|
|
||||||
where
|
|
||||||
Self: Sized,
|
|
||||||
{
|
|
||||||
self.next_back()
|
|
||||||
}
|
|
||||||
|
|
||||||
#[inline]
|
|
||||||
fn fold<Acc, Fold>(self, init: Acc, mut f: Fold) -> Acc
|
|
||||||
where
|
|
||||||
Fold: FnMut(Acc, Self::Item) -> Acc,
|
|
||||||
{
|
|
||||||
let mut accum = init;
|
|
||||||
for x in self {
|
|
||||||
accum = f(accum, x);
|
|
||||||
}
|
|
||||||
accum
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<'a> DoubleEndedIterator for Children<'a> {
|
|
||||||
#[inline]
|
|
||||||
fn next_back(&mut self) -> Option<Self::Item> {
|
|
||||||
self.inner.next_back().map(PackedGreenElement::as_ref)
|
|
||||||
}
|
|
||||||
|
|
||||||
#[inline]
|
|
||||||
fn nth_back(&mut self, n: usize) -> Option<Self::Item> {
|
|
||||||
self.inner.nth_back(n).map(PackedGreenElement::as_ref)
|
|
||||||
}
|
|
||||||
|
|
||||||
#[inline]
|
|
||||||
fn rfold<Acc, Fold>(mut self, init: Acc, mut f: Fold) -> Acc
|
|
||||||
where
|
|
||||||
Fold: FnMut(Acc, Self::Item) -> Acc,
|
|
||||||
{
|
|
||||||
let mut accum = init;
|
|
||||||
while let Some(x) = self.next_back() {
|
|
||||||
accum = f(accum, x);
|
|
||||||
}
|
|
||||||
accum
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl FusedIterator for Children<'_> {}
|
|
||||||
|
|
|
@ -65,7 +65,7 @@ pub use text_size::{TextLen, TextRange, TextSize};
|
||||||
#[doc(inline)]
|
#[doc(inline)]
|
||||||
pub use crate::syntax::*;
|
pub use crate::syntax::*;
|
||||||
pub use crate::{
|
pub use crate::{
|
||||||
green::{Checkpoint, Children, GreenNode, GreenNodeBuilder, GreenToken, NodeCache, SyntaxKind},
|
green::{Checkpoint, GreenNode, GreenNodeBuilder, GreenNodeChildren, GreenToken, NodeCache, SyntaxKind},
|
||||||
utility_types::{Direction, NodeOrToken, TokenAtOffset, WalkEvent},
|
utility_types::{Direction, NodeOrToken, TokenAtOffset, WalkEvent},
|
||||||
};
|
};
|
||||||
pub use triomphe::Arc;
|
pub use triomphe::Arc;
|
||||||
|
|
|
@ -975,7 +975,7 @@ where
|
||||||
|
|
||||||
#[derive(Clone, Debug)]
|
#[derive(Clone, Debug)]
|
||||||
struct Iter<'n> {
|
struct Iter<'n> {
|
||||||
green: Children<'n>,
|
green: GreenNodeChildren<'n>,
|
||||||
offset: TextSize,
|
offset: TextSize,
|
||||||
index: usize,
|
index: usize,
|
||||||
}
|
}
|
||||||
|
@ -983,7 +983,7 @@ struct Iter<'n> {
|
||||||
impl<'n> Iter<'n> {
|
impl<'n> Iter<'n> {
|
||||||
fn new<L: Language, D>(parent: &'n SyntaxNode<L, D>) -> Self {
|
fn new<L: Language, D>(parent: &'n SyntaxNode<L, D>) -> Self {
|
||||||
let offset = parent.text_range().start();
|
let offset = parent.text_range().start();
|
||||||
let green: Children<'_> = parent.green().children();
|
let green: GreenNodeChildren<'_> = parent.green().children();
|
||||||
Iter {
|
Iter {
|
||||||
green,
|
green,
|
||||||
offset,
|
offset,
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue