Skip to content

Commit 7f5973b

Browse files
committed
Make char count bidirectional
1 parent 08d1dd0 commit 7f5973b

1 file changed

Lines changed: 33 additions & 16 deletions

File tree

src/fallback.rs

Lines changed: 33 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -382,28 +382,45 @@ impl FileInfo {
382382
let char_index = (ch - self.span.lo) as usize;
383383

384384
// Look up offset of the largest already-computed char index that is
385-
// less than or equal to the current requested one. We resume counting
386-
// chars from that point.
387-
let (&last_char_index, &last_byte_offset) = self
385+
// less than or equal to the current requested one.
386+
let (&previous_char_index, &previous_byte_offset) = self
388387
.char_index_to_byte_offset
389388
.range(..=char_index)
390389
.next_back()
391390
.unwrap_or((&0, &0));
392391

393-
if last_char_index == char_index {
394-
last_byte_offset
395-
} else {
396-
let total_byte_offset = match self.source_text[last_byte_offset..]
397-
.char_indices()
398-
.nth(char_index - last_char_index)
399-
{
400-
Some((additional_offset, _ch)) => last_byte_offset + additional_offset,
401-
None => self.source_text.len(),
402-
};
403-
self.char_index_to_byte_offset
404-
.insert(char_index, total_byte_offset);
405-
total_byte_offset
392+
if previous_char_index == char_index {
393+
return previous_byte_offset;
406394
}
395+
396+
// Look up next char index that is greater than the requested one. We
397+
// resume counting chars from whichever point is closer.
398+
let byte_offset = match self.char_index_to_byte_offset.range(char_index..).next() {
399+
Some((&next_char_index, &next_byte_offset))
400+
if next_char_index - char_index < char_index - previous_char_index =>
401+
{
402+
self.source_text[..next_byte_offset]
403+
.char_indices()
404+
.nth_back(next_char_index - char_index - 1)
405+
.unwrap()
406+
.0
407+
}
408+
_ => {
409+
match self.source_text[previous_byte_offset..]
410+
.char_indices()
411+
.nth(char_index - previous_char_index)
412+
{
413+
Some((byte_offset_from_previous, _ch)) => {
414+
previous_byte_offset + byte_offset_from_previous
415+
}
416+
None => self.source_text.len(),
417+
}
418+
}
419+
};
420+
421+
self.char_index_to_byte_offset
422+
.insert(char_index, byte_offset);
423+
byte_offset
407424
}
408425

409426
fn source_text(&mut self, span: Span) -> String {

0 commit comments

Comments
 (0)