pub struct CodeSpans<'a> { /* private fields */ }Expand description
A text’s code/string/comment classification (per syntax), built once and queried
many times.
The amortized alternative to is_code_byte for a caller that checks several
candidate positions on the same text — e.g. every regex match a find_iter/
captures_iter pass produces on one manifest line. Build one CodeSpans per text and
call CodeSpans::is_code_byte for each candidate: the underlying scan runs once
(O(text length)) instead of once per candidate, and each query is a binary search
(O(log spans)) rather than a full rescan — turning what was an O(candidates × text
length) — quadratic under adversarial input — into O(text length + candidates ×
log(spans)) (#1022 impl-critic C1).
§Examples
use deps_core::quote_scan::{CodeSpans, ScanSyntax};
let line = r#"gem "x", path: 'vendor/git: "cache"', git: "https://real.example/r""#;
let code = CodeSpans::new(line, ScanSyntax::Ruby);
let decoy = line.find("git:").unwrap();
let real = line.rfind("git:").unwrap();
assert!(!code.is_code_byte(decoy));
assert!(code.is_code_byte(real));Implementations§
Source§impl<'a> CodeSpans<'a>
impl<'a> CodeSpans<'a>
Sourcepub fn new(text: &'a str, syntax: ScanSyntax) -> Self
pub fn new(text: &'a str, syntax: ScanSyntax) -> Self
Classifies all of text (per syntax) once, up front.
Sourcepub fn is_code_byte(&self, byte_idx: usize) -> bool
pub fn is_code_byte(&self, byte_idx: usize) -> bool
Same contract as is_code_byte, answered against the classification
CodeSpans::new already built instead of recomputing it.
self.spans covers 0..self.text.len() contiguously and in order (by
construction in scan_spans), so the span containing byte_idx, if any, is found
by binary search rather than a linear scan.