1 use std::io;
2 use std::iter::FromIterator;
3 use std::ops::RangeBounds;
4 use std::ptr;
5 use std::sync::Arc;
6 
7 use crate::crlf;
8 use crate::iter::{Bytes, Chars, Chunks, Lines};
9 use crate::rope_builder::RopeBuilder;
10 use crate::slice::RopeSlice;
11 use crate::str_utils::{
12     byte_to_char_idx, byte_to_line_idx, byte_to_utf16_surrogate_idx, char_to_byte_idx,
13     char_to_line_idx, line_to_byte_idx, line_to_char_idx, utf16_code_unit_to_char_idx,
14 };
15 use crate::tree::{Count, Node, NodeChildren, TextInfo, MAX_BYTES, MIN_BYTES};
16 use crate::{end_bound_to_num, start_bound_to_num, Error, Result};
17 
18 /// A utf8 text rope.
19 ///
20 /// The time complexity of nearly all edit and query operations on `Rope` are
21 /// worst-case `O(log N)` in the length of the rope.  `Rope` is designed to
22 /// work efficiently even for huge (in the gigabytes) and pathological (all on
23 /// one line) texts.
24 ///
25 /// # Editing Operations
26 ///
27 /// The primary editing operations on `Rope` are insertion and removal of text.
28 /// For example:
29 ///
30 /// ```
31 /// # use ropey::Rope;
32 /// #
33 /// let mut rope = Rope::from_str("Hello みんなさん!");
34 /// rope.remove(6..11);
35 /// rope.insert(6, "world");
36 ///
37 /// assert_eq!(rope, "Hello world!");
38 /// ```
39 ///
40 /// # Query Operations
41 ///
42 /// `Rope` provides a rich set of efficient query functions, including querying
43 /// rope length in bytes/`char`s/lines, fetching individual `char`s or lines,
44 /// and converting between byte/`char`/line indices.  For example, to find the
45 /// starting `char` index of a given line:
46 ///
47 /// ```
48 /// # use ropey::Rope;
49 /// #
50 /// let rope = Rope::from_str("Hello みんなさん!\nHow are you?\nThis text has multiple lines!");
51 ///
52 /// assert_eq!(rope.line_to_char(0), 0);
53 /// assert_eq!(rope.line_to_char(1), 13);
54 /// assert_eq!(rope.line_to_char(2), 26);
55 /// ```
56 ///
57 /// # Slicing
58 ///
59 /// You can take immutable slices of a `Rope` using `slice()`:
60 ///
61 /// ```
62 /// # use ropey::Rope;
63 /// #
64 /// let mut rope = Rope::from_str("Hello みんなさん!");
65 /// let middle = rope.slice(3..8);
66 ///
67 /// assert_eq!(middle, "lo みん");
68 /// ```
69 ///
70 /// # Cloning
71 ///
72 /// Cloning `Rope`s is extremely cheap, running in `O(1)` time and taking a
73 /// small constant amount of memory for the new clone, regardless of text size.
74 /// This is accomplished by data sharing between `Rope` clones.  The memory
75 /// used by clones only grows incrementally as the their contents diverge due
76 /// to edits.  All of this is thread safe, so clones can be sent freely
77 /// between threads.
78 ///
79 /// The primary intended use-case for this feature is to allow asynchronous
80 /// processing of `Rope`s.  For example, saving a large document to disk in a
81 /// separate thread while the user continues to perform edits.
82 #[derive(Clone)]
83 pub struct Rope {
84     pub(crate) root: Arc<Node>,
85 }
86 
87 impl Rope {
88     //-----------------------------------------------------------------------
89     // Constructors
90 
91     /// Creates an empty `Rope`.
92     #[inline]
new() -> Self93     pub fn new() -> Self {
94         Rope {
95             root: Arc::new(Node::new()),
96         }
97     }
98 
99     /// Creates a `Rope` from a string slice.
100     ///
101     /// Runs in O(N) time.
102     #[inline]
103     #[allow(clippy::should_implement_trait)]
from_str(text: &str) -> Self104     pub fn from_str(text: &str) -> Self {
105         RopeBuilder::new().build_at_once(text)
106     }
107 
108     /// Creates a `Rope` from the output of a reader.
109     ///
110     /// This is a convenience function, and provides *no specific guarantees*
111     /// about performance or internal implementation aside from the runtime
112     /// complexity listed below.
113     ///
114     /// When more precise control over IO behavior, buffering, etc. is desired,
115     /// you should handle IO yourself and use [`RopeBuilder`] to build the
116     /// `Rope`.
117     ///
118     /// Runs in O(N) time.
119     ///
120     /// # Errors
121     ///
122     /// - If the reader returns an error, `from_reader` stops and returns
123     ///   that error.
124     /// - If non-utf8 data is encountered, an IO error with kind
125     ///   `InvalidData` is returned.
126     ///
127     /// Note: some data from the reader is likely consumed even if there is
128     /// an error.
129     #[allow(unused_mut)]
from_reader<T: io::Read>(mut reader: T) -> io::Result<Self>130     pub fn from_reader<T: io::Read>(mut reader: T) -> io::Result<Self> {
131         const BUFFER_SIZE: usize = MAX_BYTES * 2;
132         let mut builder = RopeBuilder::new();
133         let mut buffer = [0u8; BUFFER_SIZE];
134         let mut fill_idx = 0; // How much `buffer` is currently filled with valid data
135         loop {
136             match reader.read(&mut buffer[fill_idx..]) {
137                 Ok(read_count) => {
138                     fill_idx += read_count;
139 
140                     // Determine how much of the buffer is valid utf8.
141                     let valid_count = match std::str::from_utf8(&buffer[..fill_idx]) {
142                         Ok(_) => fill_idx,
143                         Err(e) => e.valid_up_to(),
144                     };
145 
146                     // Append the valid part of the buffer to the rope.
147                     if valid_count > 0 {
148                         // The unsafe block here is reinterpreting the bytes as
149                         // utf8.  This is safe because the bytes being
150                         // reinterpreted have already been validated as utf8
151                         // just above.
152                         builder.append(unsafe {
153                             std::str::from_utf8_unchecked(&buffer[..valid_count])
154                         });
155                     }
156 
157                     // Shift the un-read part of the buffer to the beginning.
158                     if valid_count < fill_idx {
159                         // The unsafe here is just used for efficiency.  This
160                         // can be replaced with a safe call to `copy_within()`
161                         // on the slice once that API is stabalized in the
162                         // standard library.
163                         unsafe {
164                             ptr::copy(
165                                 buffer.as_ptr().add(valid_count),
166                                 buffer.as_mut_ptr().offset(0),
167                                 fill_idx - valid_count,
168                             );
169                         }
170                     }
171                     fill_idx -= valid_count;
172 
173                     if fill_idx == BUFFER_SIZE {
174                         // Buffer is full and none of it could be consumed.  Utf8
175                         // codepoints don't get that large, so it's clearly not
176                         // valid text.
177                         return Err(io::Error::new(
178                             io::ErrorKind::InvalidData,
179                             "stream did not contain valid UTF-8",
180                         ));
181                     }
182 
183                     // If we're done reading
184                     if read_count == 0 {
185                         if fill_idx > 0 {
186                             // We couldn't consume all data.
187                             return Err(io::Error::new(
188                                 io::ErrorKind::InvalidData,
189                                 "stream contained invalid UTF-8",
190                             ));
191                         } else {
192                             return Ok(builder.finish());
193                         }
194                     }
195                 }
196 
197                 Err(e) => {
198                     // Read error
199                     return Err(e);
200                 }
201             }
202         }
203     }
204 
205     //-----------------------------------------------------------------------
206     // Convenience output methods
207 
208     /// Writes the contents of the `Rope` to a writer.
209     ///
210     /// This is a convenience function, and provides *no specific guarantees*
211     /// about performance or internal implementation aside from the runtime
212     /// complexity listed below.
213     ///
214     /// When more precise control over IO behavior, buffering, etc. is
215     /// desired, you should handle IO yourself and use the [`Chunks`]
216     /// iterator to iterate through the `Rope`'s contents.
217     ///
218     /// Runs in O(N) time.
219     ///
220     /// # Errors
221     ///
222     /// - If the writer returns an error, `write_to` stops and returns that
223     ///   error.
224     ///
225     /// Note: some data may have been written even if an error is returned.
226     #[allow(unused_mut)]
write_to<T: io::Write>(&self, mut writer: T) -> io::Result<()>227     pub fn write_to<T: io::Write>(&self, mut writer: T) -> io::Result<()> {
228         for chunk in self.chunks() {
229             writer.write_all(chunk.as_bytes())?;
230         }
231 
232         Ok(())
233     }
234 
235     //-----------------------------------------------------------------------
236     // Informational methods
237 
238     /// Total number of bytes in the `Rope`.
239     ///
240     /// Runs in O(1) time.
241     #[inline]
len_bytes(&self) -> usize242     pub fn len_bytes(&self) -> usize {
243         self.root.byte_count()
244     }
245 
246     /// Total number of chars in the `Rope`.
247     ///
248     /// Runs in O(1) time.
249     #[inline]
len_chars(&self) -> usize250     pub fn len_chars(&self) -> usize {
251         self.root.char_count()
252     }
253 
254     /// Total number of lines in the `Rope`.
255     ///
256     /// Runs in O(1) time.
257     #[inline]
len_lines(&self) -> usize258     pub fn len_lines(&self) -> usize {
259         self.root.line_break_count() + 1
260     }
261 
262     /// Total number of utf16 code units that would be in `Rope` if it were
263     /// encoded as utf16.
264     ///
265     /// Ropey stores text internally as utf8, but sometimes it is necessary
266     /// to interact with external APIs that still use utf16.  This function is
267     /// primarily intended for such situations, and is otherwise not very
268     /// useful.
269     ///
270     /// Runs in O(1) time.
271     #[inline]
len_utf16_cu(&self) -> usize272     pub fn len_utf16_cu(&self) -> usize {
273         let info = self.root.text_info();
274         (info.chars + info.utf16_surrogates) as usize
275     }
276 
277     //-----------------------------------------------------------------------
278     // Memory management methods
279 
280     /// Total size of the `Rope`'s text buffer space, in bytes.
281     ///
282     /// This includes unoccupied text buffer space.  You can calculate
283     /// the unoccupied space with `capacity() - len_bytes()`.  In general,
284     /// there will always be some unoccupied buffer space.
285     ///
286     /// Runs in O(N) time.
capacity(&self) -> usize287     pub fn capacity(&self) -> usize {
288         let mut byte_count = 0;
289         for chunk in self.chunks() {
290             byte_count += chunk.len().max(MAX_BYTES);
291         }
292         byte_count
293     }
294 
295     /// Shrinks the `Rope`'s capacity to the minimum possible.
296     ///
297     /// This will rarely result in `capacity() == len_bytes()`.  `Rope`
298     /// stores text in a sequence of fixed-capacity chunks, so an exact fit
299     /// only happens for texts that are both a precise multiple of that
300     /// capacity _and_ have code point boundaries that line up exactly with
301     /// the capacity boundaries.
302     ///
303     /// After calling this, the difference between `capacity()` and
304     /// `len_bytes()` is typically under 1KB per megabyte of text in the
305     /// `Rope`.
306     ///
307     /// **NOTE:** calling this on a `Rope` clone causes it to stop sharing
308     /// all data with its other clones.  In such cases you will very likely
309     /// be _increasing_ total memory usage despite shrinking the `Rope`'s
310     /// capacity.
311     ///
312     /// Runs in O(N) time, and uses O(log N) additional space during
313     /// shrinking.
shrink_to_fit(&mut self)314     pub fn shrink_to_fit(&mut self) {
315         let mut node_stack = Vec::new();
316         let mut builder = RopeBuilder::new();
317 
318         node_stack.push(self.root.clone());
319         *self = Rope::new();
320 
321         loop {
322             if node_stack.is_empty() {
323                 break;
324             }
325 
326             if node_stack.last().unwrap().is_leaf() {
327                 builder.append(node_stack.last().unwrap().leaf_text());
328                 node_stack.pop();
329             } else if node_stack.last().unwrap().child_count() == 0 {
330                 node_stack.pop();
331             } else {
332                 let (_, next_node) = Arc::make_mut(node_stack.last_mut().unwrap())
333                     .children_mut()
334                     .remove(0);
335                 node_stack.push(next_node);
336             }
337         }
338 
339         *self = builder.finish();
340     }
341 
342     //-----------------------------------------------------------------------
343     // Edit methods
344 
345     /// Inserts `text` at char index `char_idx`.
346     ///
347     /// Runs in O(M + log N) time, where N is the length of the `Rope` and M
348     /// is the length of `text`.
349     ///
350     /// # Panics
351     ///
352     /// Panics if `char_idx` is out of bounds (i.e. `char_idx > len_chars()`).
353     #[inline]
insert(&mut self, char_idx: usize, text: &str)354     pub fn insert(&mut self, char_idx: usize, text: &str) {
355         // Bounds check
356         self.try_insert(char_idx, text).unwrap()
357     }
358 
359     /// Inserts a single char `ch` at char index `char_idx`.
360     ///
361     /// Runs in O(log N) time.
362     ///
363     /// # Panics
364     ///
365     /// Panics if `char_idx` is out of bounds (i.e. `char_idx > len_chars()`).
366     #[inline]
insert_char(&mut self, char_idx: usize, ch: char)367     pub fn insert_char(&mut self, char_idx: usize, ch: char) {
368         self.try_insert_char(char_idx, ch).unwrap()
369     }
370 
371     /// Private internal-only method that does a single insertion of
372     /// sufficiently small text.
373     ///
374     /// This only works correctly for insertion texts smaller than or equal to
375     /// `MAX_BYTES - 4`.
376     ///
377     /// Note that a lot of the complexity in this method comes from avoiding
378     /// splitting CRLF pairs and, when possible, avoiding re-scanning text for
379     /// text info.  It is otherwise conceptually fairly straightforward.
insert_internal(&mut self, char_idx: usize, ins_text: &str)380     fn insert_internal(&mut self, char_idx: usize, ins_text: &str) {
381         let mut ins_text = ins_text;
382         let mut left_seam = false;
383         let root_info = self.root.text_info();
384 
385         let (l_info, residual) = Arc::make_mut(&mut self.root).edit_chunk_at_char(
386             char_idx,
387             root_info,
388             |idx, cur_info, leaf_text| {
389                 // First check if we have a left seam.
390                 if idx == 0 && char_idx > 0 && ins_text.as_bytes()[0] == 0x0A {
391                     left_seam = true;
392                     ins_text = &ins_text[1..];
393                     // Early out if it was only an LF.
394                     if ins_text.is_empty() {
395                         return (cur_info, None);
396                     }
397                 }
398 
399                 // Find our byte index
400                 let byte_idx = char_to_byte_idx(leaf_text, idx);
401 
402                 // No node splitting
403                 if (leaf_text.len() + ins_text.len()) <= MAX_BYTES {
404                     // Calculate new info without doing a full re-scan of cur_text
405                     let new_info = {
406                         // Get summed info of current text and to-be-inserted text
407                         let mut info = cur_info + TextInfo::from_str(ins_text);
408                         // Check for CRLF pairs on the insertion seams, and
409                         // adjust line break counts accordingly
410                         if byte_idx > 0 {
411                             if leaf_text.as_bytes()[byte_idx - 1] == 0x0D
412                                 && ins_text.as_bytes()[0] == 0x0A
413                             {
414                                 info.line_breaks -= 1;
415                             }
416                             if byte_idx < leaf_text.len()
417                                 && leaf_text.as_bytes()[byte_idx - 1] == 0x0D
418                                 && leaf_text.as_bytes()[byte_idx] == 0x0A
419                             {
420                                 info.line_breaks += 1;
421                             }
422                         }
423                         if byte_idx < leaf_text.len()
424                             && *ins_text.as_bytes().last().unwrap() == 0x0D
425                             && leaf_text.as_bytes()[byte_idx] == 0x0A
426                         {
427                             info.line_breaks -= 1;
428                         }
429                         info
430                     };
431                     // Insert the text and return the new info
432                     leaf_text.insert_str(byte_idx, ins_text);
433                     (new_info, None)
434                 }
435                 // We're splitting the node
436                 else {
437                     let r_text = leaf_text.insert_str_split(byte_idx, ins_text);
438                     let l_text_info = TextInfo::from_str(&leaf_text);
439                     if r_text.len() > 0 {
440                         let r_text_info = TextInfo::from_str(&r_text);
441                         (
442                             l_text_info,
443                             Some((r_text_info, Arc::new(Node::Leaf(r_text)))),
444                         )
445                     } else {
446                         // Leaf couldn't be validly split, so leave it oversized
447                         (l_text_info, None)
448                     }
449                 }
450             },
451         );
452 
453         // Handle root splitting, if any.
454         if let Some((r_info, r_node)) = residual {
455             let mut l_node = Arc::new(Node::new());
456             std::mem::swap(&mut l_node, &mut self.root);
457 
458             let mut children = NodeChildren::new();
459             children.push((l_info, l_node));
460             children.push((r_info, r_node));
461 
462             *Arc::make_mut(&mut self.root) = Node::Internal(children);
463         }
464 
465         // Insert the LF to the left.
466         // TODO: this code feels fairly redundant with above.  Can we DRY this
467         // better?
468         if left_seam {
469             // Do the insertion
470             let root_info = self.root.text_info();
471             let (l_info, residual) = Arc::make_mut(&mut self.root).edit_chunk_at_char(
472                 char_idx - 1,
473                 root_info,
474                 |_, cur_info, leaf_text| {
475                     let byte_idx = leaf_text.len();
476 
477                     // No node splitting
478                     if (leaf_text.len() + ins_text.len()) <= MAX_BYTES {
479                         // Calculate new info without doing a full re-scan of cur_text
480                         let mut new_info = cur_info;
481                         new_info.bytes += 1;
482                         new_info.chars += 1;
483                         if *leaf_text.as_bytes().last().unwrap() != 0x0D {
484                             new_info.line_breaks += 1;
485                         }
486                         // Insert the text and return the new info
487                         leaf_text.insert_str(byte_idx, "\n");
488                         (new_info, None)
489                     }
490                     // We're splitting the node
491                     else {
492                         let r_text = leaf_text.insert_str_split(byte_idx, "\n");
493                         let l_text_info = TextInfo::from_str(&leaf_text);
494                         if r_text.len() > 0 {
495                             let r_text_info = TextInfo::from_str(&r_text);
496                             (
497                                 l_text_info,
498                                 Some((r_text_info, Arc::new(Node::Leaf(r_text)))),
499                             )
500                         } else {
501                             // Leaf couldn't be validly split, so leave it oversized
502                             (l_text_info, None)
503                         }
504                     }
505                 },
506             );
507 
508             // Handle root splitting, if any.
509             if let Some((r_info, r_node)) = residual {
510                 let mut l_node = Arc::new(Node::new());
511                 std::mem::swap(&mut l_node, &mut self.root);
512 
513                 let mut children = NodeChildren::new();
514                 children.push((l_info, l_node));
515                 children.push((r_info, r_node));
516 
517                 *Arc::make_mut(&mut self.root) = Node::Internal(children);
518             }
519         }
520     }
521 
522     /// Removes the text in the given char index range.
523     ///
524     /// Uses range syntax, e.g. `2..7`, `2..`, etc.  The range is in `char`
525     /// indices.
526     ///
527     /// Runs in O(M + log N) time, where N is the length of the `Rope` and M
528     /// is the length of the range being removed.
529     ///
530     /// # Example
531     ///
532     /// ```
533     /// # use ropey::Rope;
534     /// let mut rope = Rope::from_str("Hello world!");
535     /// rope.remove(5..);
536     ///
537     /// assert_eq!("Hello", rope);
538     /// ```
539     ///
540     /// # Panics
541     ///
542     /// Panics if the start of the range is greater than the end, or if the
543     /// end is out of bounds (i.e. `end > len_chars()`).
remove<R>(&mut self, char_range: R) where R: RangeBounds<usize>,544     pub fn remove<R>(&mut self, char_range: R)
545     where
546         R: RangeBounds<usize>,
547     {
548         self.try_remove(char_range).unwrap()
549     }
550 
551     /// Splits the `Rope` at `char_idx`, returning the right part of
552     /// the split.
553     ///
554     /// Runs in O(log N) time.
555     ///
556     /// # Panics
557     ///
558     /// Panics if `char_idx` is out of bounds (i.e. `char_idx > len_chars()`).
split_off(&mut self, char_idx: usize) -> Self559     pub fn split_off(&mut self, char_idx: usize) -> Self {
560         self.try_split_off(char_idx).unwrap()
561     }
562 
563     /// Appends a `Rope` to the end of this one, consuming the other `Rope`.
564     ///
565     /// Runs in O(log N) time.
append(&mut self, other: Self)566     pub fn append(&mut self, other: Self) {
567         if self.len_chars() == 0 {
568             // Special case
569             let mut other = other;
570             std::mem::swap(self, &mut other);
571         } else if other.len_chars() > 0 {
572             let left_info = self.root.text_info();
573             let right_info = other.root.text_info();
574 
575             let seam_byte_i = if other.char(0) == '\n' {
576                 Some(left_info.bytes)
577             } else {
578                 None
579             };
580 
581             let l_depth = self.root.depth();
582             let r_depth = other.root.depth();
583 
584             if l_depth > r_depth {
585                 let extra =
586                     Arc::make_mut(&mut self.root).append_at_depth(other.root, l_depth - r_depth);
587                 if let Some(node) = extra {
588                     let mut children = NodeChildren::new();
589                     children.push((self.root.text_info(), Arc::clone(&self.root)));
590                     children.push((node.text_info(), node));
591                     self.root = Arc::new(Node::Internal(children));
592                 }
593             } else {
594                 let mut other = other;
595                 let extra = Arc::make_mut(&mut other.root)
596                     .prepend_at_depth(Arc::clone(&self.root), r_depth - l_depth);
597                 if let Some(node) = extra {
598                     let mut children = NodeChildren::new();
599                     children.push((node.text_info(), node));
600                     children.push((other.root.text_info(), Arc::clone(&other.root)));
601                     other.root = Arc::new(Node::Internal(children));
602                 }
603                 *self = other;
604             };
605 
606             // Fix up any mess left behind.
607             let root = Arc::make_mut(&mut self.root);
608             if let Some(i) = seam_byte_i {
609                 root.fix_crlf_seam(i, true);
610             }
611             if (left_info.bytes as usize) < MIN_BYTES || (right_info.bytes as usize) < MIN_BYTES {
612                 root.fix_tree_seam(left_info.chars as usize);
613             }
614             self.pull_up_singular_nodes();
615         }
616     }
617 
618     //-----------------------------------------------------------------------
619     // Index conversion methods
620 
621     /// Returns the char index of the given byte.
622     ///
623     /// Notes:
624     ///
625     /// - If the byte is in the middle of a multi-byte char, returns the
626     ///   index of the char that the byte belongs to.
627     /// - `byte_idx` can be one-past-the-end, which will return
628     ///   one-past-the-end char index.
629     ///
630     /// Runs in O(log N) time.
631     ///
632     /// # Panics
633     ///
634     /// Panics if `byte_idx` is out of bounds (i.e. `byte_idx > len_bytes()`).
635     #[inline]
byte_to_char(&self, byte_idx: usize) -> usize636     pub fn byte_to_char(&self, byte_idx: usize) -> usize {
637         self.try_byte_to_char(byte_idx).unwrap()
638     }
639 
640     /// Returns the line index of the given byte.
641     ///
642     /// Notes:
643     ///
644     /// - Lines are zero-indexed.  This is functionally equivalent to
645     ///   counting the line endings before the specified byte.
646     /// - `byte_idx` can be one-past-the-end, which will return the
647     ///   last line index.
648     ///
649     /// Runs in O(log N) time.
650     ///
651     /// # Panics
652     ///
653     /// Panics if `byte_idx` is out of bounds (i.e. `byte_idx > len_bytes()`).
654     #[inline]
byte_to_line(&self, byte_idx: usize) -> usize655     pub fn byte_to_line(&self, byte_idx: usize) -> usize {
656         self.try_byte_to_line(byte_idx).unwrap()
657     }
658 
659     /// Returns the byte index of the given char.
660     ///
661     /// Notes:
662     ///
663     /// - `char_idx` can be one-past-the-end, which will return
664     ///   one-past-the-end byte index.
665     ///
666     /// Runs in O(log N) time.
667     ///
668     /// # Panics
669     ///
670     /// Panics if `char_idx` is out of bounds (i.e. `char_idx > len_chars()`).
671     #[inline]
char_to_byte(&self, char_idx: usize) -> usize672     pub fn char_to_byte(&self, char_idx: usize) -> usize {
673         self.try_char_to_byte(char_idx).unwrap()
674     }
675 
676     /// Returns the line index of the given char.
677     ///
678     /// Notes:
679     ///
680     /// - Lines are zero-indexed.  This is functionally equivalent to
681     ///   counting the line endings before the specified char.
682     /// - `char_idx` can be one-past-the-end, which will return the
683     ///   last line index.
684     ///
685     /// Runs in O(log N) time.
686     ///
687     /// # Panics
688     ///
689     /// Panics if `char_idx` is out of bounds (i.e. `char_idx > len_chars()`).
690     #[inline]
char_to_line(&self, char_idx: usize) -> usize691     pub fn char_to_line(&self, char_idx: usize) -> usize {
692         self.try_char_to_line(char_idx).unwrap()
693     }
694 
695     /// Returns the utf16 code unit index of the given char.
696     ///
697     /// Ropey stores text internally as utf8, but sometimes it is necessary
698     /// to interact with external APIs that still use utf16.  This function is
699     /// primarily intended for such situations, and is otherwise not very
700     /// useful.
701     ///
702     /// Runs in O(log N) time.
703     ///
704     /// # Panics
705     ///
706     /// Panics if `char_idx` is out of bounds (i.e. `char_idx > len_chars()`).
707     #[inline]
char_to_utf16_cu(&self, char_idx: usize) -> usize708     pub fn char_to_utf16_cu(&self, char_idx: usize) -> usize {
709         self.try_char_to_utf16_cu(char_idx).unwrap()
710     }
711 
712     /// Returns the char index of the given utf16 code unit.
713     ///
714     /// Ropey stores text internally as utf8, but sometimes it is necessary
715     /// to interact with external APIs that still use utf16.  This function is
716     /// primarily intended for such situations, and is otherwise not very
717     /// useful.
718     ///
719     /// Note: if the utf16 code unit is in the middle of a char, returns the
720     /// index of the char that it belongs to.
721     ///
722     /// Runs in O(log N) time.
723     ///
724     /// # Panics
725     ///
726     /// Panics if `utf16_cu_idx` is out of bounds
727     /// (i.e. `utf16_cu_idx > len_utf16_cu()`).
728     #[inline]
utf16_cu_to_char(&self, utf16_cu_idx: usize) -> usize729     pub fn utf16_cu_to_char(&self, utf16_cu_idx: usize) -> usize {
730         self.try_utf16_cu_to_char(utf16_cu_idx).unwrap()
731     }
732 
733     /// Returns the byte index of the start of the given line.
734     ///
735     /// Notes:
736     ///
737     /// - Lines are zero-indexed.
738     /// - `line_idx` can be one-past-the-end, which will return
739     ///   one-past-the-end byte index.
740     ///
741     /// Runs in O(log N) time.
742     ///
743     /// # Panics
744     ///
745     /// Panics if `line_idx` is out of bounds (i.e. `line_idx > len_lines()`).
746     #[inline]
line_to_byte(&self, line_idx: usize) -> usize747     pub fn line_to_byte(&self, line_idx: usize) -> usize {
748         self.try_line_to_byte(line_idx).unwrap()
749     }
750 
751     /// Returns the char index of the start of the given line.
752     ///
753     /// Notes:
754     ///
755     /// - Lines are zero-indexed.
756     /// - `line_idx` can be one-past-the-end, which will return
757     ///   one-past-the-end char index.
758     ///
759     /// Runs in O(log N) time.
760     ///
761     /// # Panics
762     ///
763     /// Panics if `line_idx` is out of bounds (i.e. `line_idx > len_lines()`).
764     #[inline]
line_to_char(&self, line_idx: usize) -> usize765     pub fn line_to_char(&self, line_idx: usize) -> usize {
766         self.try_line_to_char(line_idx).unwrap()
767     }
768 
769     //-----------------------------------------------------------------------
770     // Fetch methods
771 
772     /// Returns the byte at `byte_idx`.
773     ///
774     /// Runs in O(log N) time.
775     ///
776     /// # Panics
777     ///
778     /// Panics if `byte_idx` is out of bounds (i.e. `byte_idx >= len_bytes()`).
779     #[inline]
byte(&self, byte_idx: usize) -> u8780     pub fn byte(&self, byte_idx: usize) -> u8 {
781         // Bounds check
782         if let Some(out) = self.get_byte(byte_idx) {
783             out
784         } else {
785             panic!(
786                 "Attempt to index past end of Rope: byte index {}, Rope byte length {}",
787                 byte_idx,
788                 self.len_bytes()
789             );
790         }
791     }
792 
793     /// Returns the char at `char_idx`.
794     ///
795     /// Runs in O(log N) time.
796     ///
797     /// # Panics
798     ///
799     /// Panics if `char_idx` is out of bounds (i.e. `char_idx >= len_chars()`).
800     #[inline]
char(&self, char_idx: usize) -> char801     pub fn char(&self, char_idx: usize) -> char {
802         if let Some(out) = self.get_char(char_idx) {
803             out
804         } else {
805             panic!(
806                 "Attempt to index past end of Rope: char index {}, Rope char length {}",
807                 char_idx,
808                 self.len_chars()
809             );
810         }
811     }
812 
813     /// Returns the line at `line_idx`.
814     ///
815     /// Note: lines are zero-indexed.
816     ///
817     /// Runs in O(log N) time.
818     ///
819     /// # Panics
820     ///
821     /// Panics if `line_idx` is out of bounds (i.e. `line_idx >= len_lines()`).
822     #[inline]
line(&self, line_idx: usize) -> RopeSlice823     pub fn line(&self, line_idx: usize) -> RopeSlice {
824         if let Some(out) = self.get_line(line_idx) {
825             out
826         } else {
827             let len_lines = self.len_lines();
828             panic!(
829                 "Attempt to index past end of Rope: line index {}, Rope line length {}",
830                 line_idx, len_lines
831             );
832         }
833     }
834 
835     /// Returns the chunk containing the given byte index.
836     ///
837     /// Also returns the byte and char indices of the beginning of the chunk
838     /// and the index of the line that the chunk starts on.
839     ///
840     /// Note: for convenience, a one-past-the-end `byte_idx` returns the last
841     /// chunk of the `RopeSlice`.
842     ///
843     /// The return value is organized as
844     /// `(chunk, chunk_byte_idx, chunk_char_idx, chunk_line_idx)`.
845     ///
846     /// Runs in O(log N) time.
847     ///
848     /// # Panics
849     ///
850     /// Panics if `byte_idx` is out of bounds (i.e. `byte_idx > len_bytes()`).
851     #[inline]
chunk_at_byte(&self, byte_idx: usize) -> (&str, usize, usize, usize)852     pub fn chunk_at_byte(&self, byte_idx: usize) -> (&str, usize, usize, usize) {
853         // Bounds check
854         if let Some(out) = self.get_chunk_at_byte(byte_idx) {
855             out
856         } else {
857             panic!(
858                 "Attempt to index past end of Rope: byte index {}, Rope byte length {}",
859                 byte_idx,
860                 self.len_bytes()
861             );
862         }
863     }
864 
865     /// Returns the chunk containing the given char index.
866     ///
867     /// Also returns the byte and char indices of the beginning of the chunk
868     /// and the index of the line that the chunk starts on.
869     ///
870     /// Note: for convenience, a one-past-the-end `char_idx` returns the last
871     /// chunk of the `RopeSlice`.
872     ///
873     /// The return value is organized as
874     /// `(chunk, chunk_byte_idx, chunk_char_idx, chunk_line_idx)`.
875     ///
876     /// Runs in O(log N) time.
877     ///
878     /// # Panics
879     ///
880     /// Panics if `char_idx` is out of bounds (i.e. `char_idx > len_chars()`).
881     #[inline]
chunk_at_char(&self, char_idx: usize) -> (&str, usize, usize, usize)882     pub fn chunk_at_char(&self, char_idx: usize) -> (&str, usize, usize, usize) {
883         if let Some(out) = self.get_chunk_at_char(char_idx) {
884             out
885         } else {
886             panic!(
887                 "Attempt to index past end of Rope: char index {}, Rope char length {}",
888                 char_idx,
889                 self.len_chars()
890             );
891         }
892     }
893 
894     /// Returns the chunk containing the given line break.
895     ///
896     /// Also returns the byte and char indices of the beginning of the chunk
897     /// and the index of the line that the chunk starts on.
898     ///
899     /// Note: for convenience, both the beginning and end of the rope are
900     /// considered line breaks for the purposes of indexing.  For example, in
901     /// the string `"Hello \n world!"` 0 would give the first chunk, 1 would
902     /// give the chunk containing the newline character, and 2 would give the
903     /// last chunk.
904     ///
905     /// The return value is organized as
906     /// `(chunk, chunk_byte_idx, chunk_char_idx, chunk_line_idx)`.
907     ///
908     /// Runs in O(log N) time.
909     ///
910     /// # Panics
911     ///
912     /// Panics if `line_break_idx` is out of bounds (i.e. `line_break_idx > len_lines()`).
913     #[inline]
chunk_at_line_break(&self, line_break_idx: usize) -> (&str, usize, usize, usize)914     pub fn chunk_at_line_break(&self, line_break_idx: usize) -> (&str, usize, usize, usize) {
915         if let Some(out) = self.get_chunk_at_line_break(line_break_idx) {
916             out
917         } else {
918             panic!(
919                 "Attempt to index past end of Rope: line break index {}, max index {}",
920                 line_break_idx,
921                 self.len_lines()
922             );
923         }
924     }
925 
926     //-----------------------------------------------------------------------
927     // Slicing
928 
929     /// Gets an immutable slice of the `Rope`.
930     ///
931     /// Uses range syntax, e.g. `2..7`, `2..`, etc.
932     ///
933     /// # Example
934     ///
935     /// ```
936     /// # use ropey::Rope;
937     /// let rope = Rope::from_str("Hello world!");
938     /// let slice = rope.slice(..5);
939     ///
940     /// assert_eq!("Hello", slice);
941     /// ```
942     ///
943     /// Runs in O(log N) time.
944     ///
945     /// # Panics
946     ///
947     /// Panics if the start of the range is greater than the end, or if the
948     /// end is out of bounds (i.e. `end > len_chars()`).
949     #[inline]
slice<R>(&self, char_range: R) -> RopeSlice where R: RangeBounds<usize>,950     pub fn slice<R>(&self, char_range: R) -> RopeSlice
951     where
952         R: RangeBounds<usize>,
953     {
954         self.get_slice(char_range).unwrap()
955     }
956 
957     //-----------------------------------------------------------------------
958     // Iterator methods
959 
960     /// Creates an iterator over the bytes of the `Rope`.
961     ///
962     /// Runs in O(log N) time.
963     #[inline]
bytes(&self) -> Bytes964     pub fn bytes(&self) -> Bytes {
965         Bytes::new(&self.root)
966     }
967 
968     /// Creates an iterator over the bytes of the `Rope`, starting at byte
969     /// `byte_idx`.
970     ///
971     /// If `byte_idx == len_bytes()` then an iterator at the end of the
972     /// `Rope` is created (i.e. `next()` will return `None`).
973     ///
974     /// Runs in O(log N) time.
975     ///
976     /// # Panics
977     ///
978     /// Panics if `byte_idx` is out of bounds (i.e. `byte_idx > len_bytes()`).
979     #[inline]
bytes_at(&self, byte_idx: usize) -> Bytes980     pub fn bytes_at(&self, byte_idx: usize) -> Bytes {
981         if let Some(out) = self.get_bytes_at(byte_idx) {
982             out
983         } else {
984             panic!(
985                 "Attempt to index past end of Rope: byte index {}, Rope byte length {}",
986                 byte_idx,
987                 self.len_bytes()
988             );
989         }
990     }
991 
992     /// Creates an iterator over the chars of the `Rope`.
993     ///
994     /// Runs in O(log N) time.
995     #[inline]
chars(&self) -> Chars996     pub fn chars(&self) -> Chars {
997         Chars::new(&self.root)
998     }
999 
1000     /// Creates an iterator over the chars of the `Rope`, starting at char
1001     /// `char_idx`.
1002     ///
1003     /// If `char_idx == len_chars()` then an iterator at the end of the
1004     /// `Rope` is created (i.e. `next()` will return `None`).
1005     ///
1006     /// Runs in O(log N) time.
1007     ///
1008     /// # Panics
1009     ///
1010     /// Panics if `char_idx` is out of bounds (i.e. `char_idx > len_chars()`).
1011     #[inline]
chars_at(&self, char_idx: usize) -> Chars1012     pub fn chars_at(&self, char_idx: usize) -> Chars {
1013         if let Some(out) = self.get_chars_at(char_idx) {
1014             out
1015         } else {
1016             panic!(
1017                 "Attempt to index past end of Rope: char index {}, Rope char length {}",
1018                 char_idx,
1019                 self.len_chars()
1020             );
1021         }
1022     }
1023 
1024     /// Creates an iterator over the lines of the `Rope`.
1025     ///
1026     /// Runs in O(log N) time.
1027     #[inline]
lines(&self) -> Lines1028     pub fn lines(&self) -> Lines {
1029         Lines::new(&self.root)
1030     }
1031 
1032     /// Creates an iterator over the lines of the `Rope`, starting at line
1033     /// `line_idx`.
1034     ///
1035     /// If `line_idx == len_lines()` then an iterator at the end of the
1036     /// `Rope` is created (i.e. `next()` will return `None`).
1037     ///
1038     /// Runs in O(log N) time.
1039     ///
1040     /// # Panics
1041     ///
1042     /// Panics if `line_idx` is out of bounds (i.e. `line_idx > len_lines()`).
1043     #[inline]
lines_at(&self, line_idx: usize) -> Lines1044     pub fn lines_at(&self, line_idx: usize) -> Lines {
1045         if let Some(out) = self.get_lines_at(line_idx) {
1046             out
1047         } else {
1048             panic!(
1049                 "Attempt to index past end of Rope: line index {}, Rope line length {}",
1050                 line_idx,
1051                 self.len_lines()
1052             );
1053         }
1054     }
1055 
1056     /// Creates an iterator over the chunks of the `Rope`.
1057     ///
1058     /// Runs in O(log N) time.
1059     #[inline]
chunks(&self) -> Chunks1060     pub fn chunks(&self) -> Chunks {
1061         Chunks::new(&self.root)
1062     }
1063 
1064     /// Creates an iterator over the chunks of the `Rope`, with the
1065     /// iterator starting at the chunk containing `byte_idx`.
1066     ///
1067     /// Also returns the byte and char indices of the beginning of the first
1068     /// chunk to be yielded, and the index of the line that chunk starts on.
1069     ///
1070     /// If `byte_idx == len_bytes()` an iterator at the end of the `Rope`
1071     /// (yielding `None` on a call to `next()`) is created.
1072     ///
1073     /// The return value is organized as
1074     /// `(iterator, chunk_byte_idx, chunk_char_idx, chunk_line_idx)`.
1075     ///
1076     /// Runs in O(log N) time.
1077     ///
1078     /// # Panics
1079     ///
1080     /// Panics if `byte_idx` is out of bounds (i.e. `byte_idx > len_bytes()`).
1081     #[inline]
chunks_at_byte(&self, byte_idx: usize) -> (Chunks, usize, usize, usize)1082     pub fn chunks_at_byte(&self, byte_idx: usize) -> (Chunks, usize, usize, usize) {
1083         if let Some(out) = self.get_chunks_at_byte(byte_idx) {
1084             out
1085         } else {
1086             panic!(
1087                 "Attempt to index past end of Rope: byte index {}, Rope byte length {}",
1088                 byte_idx,
1089                 self.len_bytes()
1090             );
1091         }
1092     }
1093 
1094     /// Creates an iterator over the chunks of the `Rope`, with the
1095     /// iterator starting at the chunk containing `char_idx`.
1096     ///
1097     /// Also returns the byte and char indices of the beginning of the first
1098     /// chunk to be yielded, and the index of the line that chunk starts on.
1099     ///
1100     /// If `char_idx == len_chars()` an iterator at the end of the `Rope`
1101     /// (yielding `None` on a call to `next()`) is created.
1102     ///
1103     /// The return value is organized as
1104     /// `(iterator, chunk_byte_idx, chunk_char_idx, chunk_line_idx)`.
1105     ///
1106     /// Runs in O(log N) time.
1107     ///
1108     /// # Panics
1109     ///
1110     /// Panics if `char_idx` is out of bounds (i.e. `char_idx > len_chars()`).
1111     #[inline]
chunks_at_char(&self, char_idx: usize) -> (Chunks, usize, usize, usize)1112     pub fn chunks_at_char(&self, char_idx: usize) -> (Chunks, usize, usize, usize) {
1113         if let Some(out) = self.get_chunks_at_char(char_idx) {
1114             out
1115         } else {
1116             panic!(
1117                 "Attempt to index past end of Rope: char index {}, Rope char length {}",
1118                 char_idx,
1119                 self.len_chars()
1120             );
1121         }
1122     }
1123 
1124     /// Creates an iterator over the chunks of the `Rope`, with the
1125     /// iterator starting at the chunk containing `line_break_idx`.
1126     ///
1127     /// Also returns the byte and char indices of the beginning of the first
1128     /// chunk to be yielded, and the index of the line that chunk starts on.
1129     ///
1130     /// Note: for convenience, both the beginning and end of the `Rope` are
1131     /// considered line breaks for the purposes of indexing.  For example, in
1132     /// the string `"Hello \n world!"` 0 would create an iterator starting on
1133     /// the first chunk, 1 would create an iterator starting on the chunk
1134     /// containing the newline character, and 2 would create an iterator at
1135     /// the end of the `Rope` (yielding `None` on a call to `next()`).
1136     ///
1137     /// The return value is organized as
1138     /// `(iterator, chunk_byte_idx, chunk_char_idx, chunk_line_idx)`.
1139     ///
1140     /// Runs in O(log N) time.
1141     ///
1142     /// # Panics
1143     ///
1144     /// Panics if `line_break_idx` is out of bounds (i.e. `line_break_idx > len_lines()`).
1145     #[inline]
chunks_at_line_break(&self, line_break_idx: usize) -> (Chunks, usize, usize, usize)1146     pub fn chunks_at_line_break(&self, line_break_idx: usize) -> (Chunks, usize, usize, usize) {
1147         if let Some(out) = self.get_chunks_at_line_break(line_break_idx) {
1148             out
1149         } else {
1150             panic!(
1151                 "Attempt to index past end of Rope: line break index {}, max index {}",
1152                 line_break_idx,
1153                 self.len_lines()
1154             );
1155         }
1156     }
1157 
1158     //-----------------------------------------------------------------------
1159     // Debugging
1160 
1161     /// NOT PART OF THE PUBLIC API (hidden from docs for a reason!)
1162     ///
1163     /// Debugging tool to make sure that all of the meta-data of the
1164     /// tree is consistent with the actual data.
1165     #[doc(hidden)]
assert_integrity(&self)1166     pub fn assert_integrity(&self) {
1167         self.root.assert_integrity();
1168     }
1169 
1170     /// NOT PART OF THE PUBLIC API (hidden from docs for a reason!)
1171     ///
1172     /// Debugging tool to make sure that all of the following invariants
1173     /// hold true throughout the tree:
1174     ///
1175     /// - The tree is the same height everywhere.
1176     /// - All internal nodes have the minimum number of children.
1177     /// - All leaf nodes are non-empty.
1178     /// - CRLF pairs are never split over chunk boundaries.
1179     #[doc(hidden)]
assert_invariants(&self)1180     pub fn assert_invariants(&self) {
1181         self.root.assert_balance();
1182         self.root.assert_node_size(true);
1183         self.assert_crlf_seams();
1184     }
1185 
1186     /// Checks that CRLF pairs are never split over chunk boundaries.
assert_crlf_seams(&self)1187     fn assert_crlf_seams(&self) {
1188         if self.chunks().count() > 0 {
1189             let mut itr = self.chunks();
1190             let mut last_chunk = itr.next().unwrap();
1191             for chunk in itr {
1192                 if !chunk.is_empty() && !last_chunk.is_empty() {
1193                     assert!(crlf::seam_is_break(last_chunk.as_bytes(), chunk.as_bytes()));
1194                     last_chunk = chunk;
1195                 } else if last_chunk.is_empty() {
1196                     last_chunk = chunk;
1197                 }
1198             }
1199         }
1200     }
1201 
1202     //-----------------------------------------------------------------------
1203     // Internal utilities
1204 
1205     /// Iteratively replaces the root node with its child if it only has
1206     /// one child.
pull_up_singular_nodes(&mut self)1207     pub(crate) fn pull_up_singular_nodes(&mut self) {
1208         while (!self.root.is_leaf()) && self.root.child_count() == 1 {
1209             let child = if let Node::Internal(ref children) = *self.root {
1210                 Arc::clone(&children.nodes()[0])
1211             } else {
1212                 unreachable!()
1213             };
1214 
1215             self.root = child;
1216         }
1217     }
1218 }
1219 
1220 /// # Non-Panicking
1221 ///
1222 /// The methods in this impl block provide non-panicking versions of
1223 /// `Rope`'s panicking methods.  They return either `Option::None` or
1224 /// `Result::Err()` when their panicking counterparts would have panicked.
1225 impl Rope {
1226     /// Non-panicking version of [`insert()`](Rope::insert).
1227     #[inline]
try_insert(&mut self, char_idx: usize, text: &str) -> Result<()>1228     pub fn try_insert(&mut self, char_idx: usize, text: &str) -> Result<()> {
1229         // Bounds check
1230         if char_idx <= self.len_chars() {
1231             // We have three cases here:
1232             // 1. The insertion text is very large, in which case building a new
1233             //    Rope out of it and splicing it into the existing Rope is most
1234             //    efficient.
1235             // 2. The insertion text is somewhat large, in which case splitting it
1236             //    up into chunks and repeatedly inserting them is the most
1237             //    efficient.  The splitting is necessary because the insertion code
1238             //    only works correctly below a certain insertion size.
1239             // 3. The insertion text is small, in which case we can simply insert
1240             //    it.
1241             //
1242             // Cases #2 and #3 are rolled into one case here, where case #3 just
1243             // results in the text being "split" into only one chunk.
1244             //
1245             // The boundary for what constitutes "very large" text was arrived at
1246             // experimentally, by testing at what point Rope build + splice becomes
1247             // faster than split + repeated insert.  This constant is likely worth
1248             // revisiting from time to time as Ropey evolves.
1249             if text.len() > MAX_BYTES * 6 {
1250                 // Case #1: very large text, build rope and splice it in.
1251                 let text_rope = Rope::from_str(text);
1252                 let right = self.split_off(char_idx);
1253                 self.append(text_rope);
1254                 self.append(right);
1255             } else {
1256                 // Cases #2 and #3: split into chunks and repeatedly insert.
1257                 let mut text = text;
1258                 while !text.is_empty() {
1259                     // Split a chunk off from the end of the text.
1260                     // We do this from the end instead of the front so that
1261                     // the repeated insertions can keep re-using the same
1262                     // insertion point.
1263                     let split_idx = crlf::find_good_split(
1264                         text.len() - (MAX_BYTES - 4).min(text.len()),
1265                         text.as_bytes(),
1266                         false,
1267                     );
1268                     let ins_text = &text[split_idx..];
1269                     text = &text[..split_idx];
1270 
1271                     // Do the insertion.
1272                     self.insert_internal(char_idx, ins_text);
1273                 }
1274             }
1275             Ok(())
1276         } else {
1277             Err(Error::CharIndexOutOfBounds(char_idx, self.len_chars()))
1278         }
1279     }
1280 
1281     /// Non-panicking version of [`insert_char()`](Rope::insert_char).
1282     #[inline]
try_insert_char(&mut self, char_idx: usize, ch: char) -> Result<()>1283     pub fn try_insert_char(&mut self, char_idx: usize, ch: char) -> Result<()> {
1284         // Bounds check
1285         if char_idx <= self.len_chars() {
1286             let mut buf = [0u8; 4];
1287             Ok(self.insert_internal(char_idx, ch.encode_utf8(&mut buf)))
1288         } else {
1289             Err(Error::CharIndexOutOfBounds(char_idx, self.len_chars()))
1290         }
1291     }
1292 
1293     /// Non-panicking version of [`remove()`](Rope::remove).
try_remove<R>(&mut self, char_range: R) -> Result<()> where R: RangeBounds<usize>,1294     pub fn try_remove<R>(&mut self, char_range: R) -> Result<()>
1295     where
1296         R: RangeBounds<usize>,
1297     {
1298         let start_opt = start_bound_to_num(char_range.start_bound());
1299         let end_opt = end_bound_to_num(char_range.end_bound());
1300         let start = start_opt.unwrap_or(0);
1301         let end = end_opt.unwrap_or_else(|| self.len_chars());
1302         if !(end.max(start) <= self.len_chars()) {
1303             Err(Error::CharRangeOutOfBounds(
1304                 start_opt,
1305                 end_opt,
1306                 self.len_chars(),
1307             ))
1308         } else if !(start <= end) {
1309             Err(Error::CharRangeInvalid(start, end))
1310         } else {
1311             // A special case that the rest of the logic doesn't handle
1312             // correctly.
1313             if start == 0 && end == self.len_chars() {
1314                 self.root = Arc::new(Node::new());
1315                 return Ok(());
1316             }
1317 
1318             let root = Arc::make_mut(&mut self.root);
1319 
1320             let root_info = root.text_info();
1321             let (_, crlf_seam, needs_fix) = root.remove_char_range(start, end, root_info);
1322 
1323             if crlf_seam {
1324                 let seam_idx = root.char_to_text_info(start).bytes;
1325                 root.fix_crlf_seam(seam_idx as Count, false);
1326             }
1327 
1328             if needs_fix {
1329                 root.fix_tree_seam(start);
1330             }
1331 
1332             self.pull_up_singular_nodes();
1333             Ok(())
1334         }
1335     }
1336 
1337     /// Non-panicking version of [`split_off()`](Rope::split_off).
try_split_off(&mut self, char_idx: usize) -> Result<Self>1338     pub fn try_split_off(&mut self, char_idx: usize) -> Result<Self> {
1339         // Bounds check
1340         if char_idx <= self.len_chars() {
1341             if char_idx == 0 {
1342                 // Special case 1
1343                 let mut new_rope = Rope::new();
1344                 std::mem::swap(self, &mut new_rope);
1345                 Ok(new_rope)
1346             } else if char_idx == self.len_chars() {
1347                 // Special case 2
1348                 Ok(Rope::new())
1349             } else {
1350                 // Do the split
1351                 let mut new_rope = Rope {
1352                     root: Arc::new(Arc::make_mut(&mut self.root).split(char_idx)),
1353                 };
1354 
1355                 // Fix up the edges
1356                 Arc::make_mut(&mut self.root).zip_fix_right();
1357                 Arc::make_mut(&mut new_rope.root).zip_fix_left();
1358                 self.pull_up_singular_nodes();
1359                 new_rope.pull_up_singular_nodes();
1360 
1361                 Ok(new_rope)
1362             }
1363         } else {
1364             Err(Error::CharIndexOutOfBounds(char_idx, self.len_chars()))
1365         }
1366     }
1367 
1368     /// Non-panicking version of [`byte_to_char()`](Rope::byte_to_char).
1369     #[inline]
try_byte_to_char(&self, byte_idx: usize) -> Result<usize>1370     pub fn try_byte_to_char(&self, byte_idx: usize) -> Result<usize> {
1371         // Bounds check
1372         if byte_idx <= self.len_bytes() {
1373             let (chunk, b, c, _) = self.chunk_at_byte(byte_idx);
1374             Ok(c + byte_to_char_idx(chunk, byte_idx - b))
1375         } else {
1376             Err(Error::ByteIndexOutOfBounds(byte_idx, self.len_bytes()))
1377         }
1378     }
1379 
1380     /// Non-panicking version of [`byte_to_line()`](Rope::byte_to_line).
1381     #[inline]
try_byte_to_line(&self, byte_idx: usize) -> Result<usize>1382     pub fn try_byte_to_line(&self, byte_idx: usize) -> Result<usize> {
1383         // Bounds check
1384         if byte_idx <= self.len_bytes() {
1385             let (chunk, b, _, l) = self.chunk_at_byte(byte_idx);
1386             Ok(l + byte_to_line_idx(chunk, byte_idx - b))
1387         } else {
1388             Err(Error::ByteIndexOutOfBounds(byte_idx, self.len_bytes()))
1389         }
1390     }
1391 
1392     /// Non-panicking version of [`char_to_byte()`](Rope::char_to_byte).
1393     #[inline]
try_char_to_byte(&self, char_idx: usize) -> Result<usize>1394     pub fn try_char_to_byte(&self, char_idx: usize) -> Result<usize> {
1395         // Bounds check
1396         if char_idx <= self.len_chars() {
1397             let (chunk, b, c, _) = self.chunk_at_char(char_idx);
1398             Ok(b + char_to_byte_idx(chunk, char_idx - c))
1399         } else {
1400             Err(Error::CharIndexOutOfBounds(char_idx, self.len_chars()))
1401         }
1402     }
1403 
1404     /// Non-panicking version of [`char_to_line()`](Rope::char_to_line).
1405     #[inline]
try_char_to_line(&self, char_idx: usize) -> Result<usize>1406     pub fn try_char_to_line(&self, char_idx: usize) -> Result<usize> {
1407         // Bounds check
1408         if char_idx <= self.len_chars() {
1409             let (chunk, _, c, l) = self.chunk_at_char(char_idx);
1410             Ok(l + char_to_line_idx(chunk, char_idx - c))
1411         } else {
1412             Err(Error::CharIndexOutOfBounds(char_idx, self.len_chars()))
1413         }
1414     }
1415 
1416     /// Non-panicking version of [`char_to_utf16_cu()`](Rope::char_to_utf16_cu).
1417     #[inline]
try_char_to_utf16_cu(&self, char_idx: usize) -> Result<usize>1418     pub fn try_char_to_utf16_cu(&self, char_idx: usize) -> Result<usize> {
1419         // Bounds check
1420         if char_idx <= self.len_chars() {
1421             let (chunk, chunk_start_info) = self.root.get_chunk_at_char(char_idx);
1422             let chunk_byte_idx =
1423                 char_to_byte_idx(chunk, char_idx - chunk_start_info.chars as usize);
1424             let surrogate_count = byte_to_utf16_surrogate_idx(chunk, chunk_byte_idx);
1425 
1426             Ok(char_idx + chunk_start_info.utf16_surrogates as usize + surrogate_count)
1427         } else {
1428             Err(Error::CharIndexOutOfBounds(char_idx, self.len_chars()))
1429         }
1430     }
1431 
1432     /// Non-panicking version of [`utf16_cu_to_char()`](Rope::utf16_cu_to_char).
1433     #[inline]
try_utf16_cu_to_char(&self, utf16_cu_idx: usize) -> Result<usize>1434     pub fn try_utf16_cu_to_char(&self, utf16_cu_idx: usize) -> Result<usize> {
1435         // Bounds check
1436         if utf16_cu_idx <= self.len_utf16_cu() {
1437             let (chunk, chunk_start_info) = self.root.get_chunk_at_utf16_code_unit(utf16_cu_idx);
1438             let chunk_utf16_cu_idx = utf16_cu_idx
1439                 - (chunk_start_info.chars + chunk_start_info.utf16_surrogates) as usize;
1440             let chunk_char_idx = utf16_code_unit_to_char_idx(chunk, chunk_utf16_cu_idx);
1441 
1442             Ok(chunk_start_info.chars as usize + chunk_char_idx)
1443         } else {
1444             Err(Error::Utf16IndexOutOfBounds(
1445                 utf16_cu_idx,
1446                 self.len_utf16_cu(),
1447             ))
1448         }
1449     }
1450 
1451     /// Non-panicking version of [`line_to_byte()`](Rope::line_to_byte).
1452     #[inline]
try_line_to_byte(&self, line_idx: usize) -> Result<usize>1453     pub fn try_line_to_byte(&self, line_idx: usize) -> Result<usize> {
1454         // Bounds check
1455         if line_idx <= self.len_lines() {
1456             if line_idx == self.len_lines() {
1457                 Ok(self.len_bytes())
1458             } else {
1459                 let (chunk, b, _, l) = self.chunk_at_line_break(line_idx);
1460                 Ok(b + line_to_byte_idx(chunk, line_idx - l))
1461             }
1462         } else {
1463             Err(Error::LineIndexOutOfBounds(line_idx, self.len_lines()))
1464         }
1465     }
1466 
1467     /// Non-panicking version of [`line_to_char()`](Rope::line_to_char).
1468     #[inline]
try_line_to_char(&self, line_idx: usize) -> Result<usize>1469     pub fn try_line_to_char(&self, line_idx: usize) -> Result<usize> {
1470         // Bounds check
1471         if line_idx <= self.len_lines() {
1472             if line_idx == self.len_lines() {
1473                 Ok(self.len_chars())
1474             } else {
1475                 let (chunk, _, c, l) = self.chunk_at_line_break(line_idx);
1476                 Ok(c + line_to_char_idx(chunk, line_idx - l))
1477             }
1478         } else {
1479             Err(Error::LineIndexOutOfBounds(line_idx, self.len_lines()))
1480         }
1481     }
1482 
1483     /// Non-panicking version of [`byte()`](Rope::byte).
1484     #[inline]
get_byte(&self, byte_idx: usize) -> Option<u8>1485     pub fn get_byte(&self, byte_idx: usize) -> Option<u8> {
1486         // Bounds check
1487         if byte_idx < self.len_bytes() {
1488             let (chunk, chunk_byte_idx, _, _) = self.chunk_at_byte(byte_idx);
1489             let chunk_rel_byte_idx = byte_idx - chunk_byte_idx;
1490             Some(chunk.as_bytes()[chunk_rel_byte_idx])
1491         } else {
1492             None
1493         }
1494     }
1495 
1496     /// Non-panicking version of [`char()`](Rope::char).
1497     #[inline]
get_char(&self, char_idx: usize) -> Option<char>1498     pub fn get_char(&self, char_idx: usize) -> Option<char> {
1499         // Bounds check
1500         if char_idx < self.len_chars() {
1501             let (chunk, _, chunk_char_idx, _) = self.chunk_at_char(char_idx);
1502             let byte_idx = char_to_byte_idx(chunk, char_idx - chunk_char_idx);
1503             Some(chunk[byte_idx..].chars().next().unwrap())
1504         } else {
1505             None
1506         }
1507     }
1508 
1509     /// Non-panicking version of [`line()`](Rope::line).
1510     #[inline]
get_line(&self, line_idx: usize) -> Option<RopeSlice>1511     pub fn get_line(&self, line_idx: usize) -> Option<RopeSlice> {
1512         use crate::slice::RSEnum;
1513         use crate::str_utils::{count_chars, count_utf16_surrogates};
1514 
1515         let len_lines = self.len_lines();
1516 
1517         // Bounds check
1518         if line_idx < len_lines {
1519             let (chunk_1, _, c1, l1) = self.chunk_at_line_break(line_idx);
1520             let (chunk_2, _, c2, l2) = self.chunk_at_line_break(line_idx + 1);
1521             if c1 == c2 {
1522                 let text1 = &chunk_1[line_to_byte_idx(chunk_1, line_idx - l1)..];
1523                 let text2 = &text1[..line_to_byte_idx(text1, 1)];
1524                 Some(RopeSlice(RSEnum::Light {
1525                     text: text2,
1526                     char_count: count_chars(text2) as Count,
1527                     utf16_surrogate_count: count_utf16_surrogates(text2) as Count,
1528                     line_break_count: if line_idx == (len_lines - 1) { 0 } else { 1 },
1529                 }))
1530             } else {
1531                 let start = c1 + line_to_char_idx(chunk_1, line_idx - l1);
1532                 let end = c2 + line_to_char_idx(chunk_2, line_idx + 1 - l2);
1533                 Some(self.slice(start..end))
1534             }
1535         } else {
1536             None
1537         }
1538     }
1539 
1540     /// Non-panicking version of [`chunk_at_byte()`](Rope::chunk_at_byte).
1541     #[inline]
get_chunk_at_byte(&self, byte_idx: usize) -> Option<(&str, usize, usize, usize)>1542     pub fn get_chunk_at_byte(&self, byte_idx: usize) -> Option<(&str, usize, usize, usize)> {
1543         // Bounds check
1544         if byte_idx <= self.len_bytes() {
1545             let (chunk, info) = self.root.get_chunk_at_byte(byte_idx);
1546             Some((
1547                 chunk,
1548                 info.bytes as usize,
1549                 info.chars as usize,
1550                 info.line_breaks as usize,
1551             ))
1552         } else {
1553             None
1554         }
1555     }
1556 
1557     /// Non-panicking version of [`chunk_at_char()`](Rope::chunk_at_char).
1558     #[inline]
get_chunk_at_char(&self, char_idx: usize) -> Option<(&str, usize, usize, usize)>1559     pub fn get_chunk_at_char(&self, char_idx: usize) -> Option<(&str, usize, usize, usize)> {
1560         // Bounds check
1561         if char_idx <= self.len_chars() {
1562             let (chunk, info) = self.root.get_chunk_at_char(char_idx);
1563             Some((
1564                 chunk,
1565                 info.bytes as usize,
1566                 info.chars as usize,
1567                 info.line_breaks as usize,
1568             ))
1569         } else {
1570             None
1571         }
1572     }
1573 
1574     /// Non-panicking version of [`chunk_at_line_break()`](Rope::chunk_at_line_break).
1575     #[inline]
get_chunk_at_line_break( &self, line_break_idx: usize, ) -> Option<(&str, usize, usize, usize)>1576     pub fn get_chunk_at_line_break(
1577         &self,
1578         line_break_idx: usize,
1579     ) -> Option<(&str, usize, usize, usize)> {
1580         // Bounds check
1581         if line_break_idx <= self.len_lines() {
1582             let (chunk, info) = self.root.get_chunk_at_line_break(line_break_idx);
1583             Some((
1584                 chunk,
1585                 info.bytes as usize,
1586                 info.chars as usize,
1587                 info.line_breaks as usize,
1588             ))
1589         } else {
1590             None
1591         }
1592     }
1593 
1594     /// Non-panicking version of [`slice()`](Rope::slice).
1595     #[inline]
get_slice<R>(&self, char_range: R) -> Option<RopeSlice> where R: RangeBounds<usize>,1596     pub fn get_slice<R>(&self, char_range: R) -> Option<RopeSlice>
1597     where
1598         R: RangeBounds<usize>,
1599     {
1600         let start = start_bound_to_num(char_range.start_bound()).unwrap_or(0);
1601         let end = end_bound_to_num(char_range.end_bound()).unwrap_or_else(|| self.len_chars());
1602 
1603         // Bounds check
1604         if start <= end && end <= self.len_chars() {
1605             Some(RopeSlice::new_with_range(&self.root, start, end))
1606         } else {
1607             None
1608         }
1609     }
1610 
1611     /// Non-panicking version of [`bytes_at()`](Rope::bytes_at).
1612     #[inline]
get_bytes_at(&self, byte_idx: usize) -> Option<Bytes>1613     pub fn get_bytes_at(&self, byte_idx: usize) -> Option<Bytes> {
1614         // Bounds check
1615         if byte_idx <= self.len_bytes() {
1616             let info = self.root.text_info();
1617             Some(Bytes::new_with_range_at(
1618                 &self.root,
1619                 byte_idx,
1620                 (0, info.bytes as usize),
1621                 (0, info.chars as usize),
1622                 (0, info.line_breaks as usize + 1),
1623             ))
1624         } else {
1625             None
1626         }
1627     }
1628 
1629     /// Non-panicking version of [`chars_at()`](Rope::chars_at).
1630     #[inline]
get_chars_at(&self, char_idx: usize) -> Option<Chars>1631     pub fn get_chars_at(&self, char_idx: usize) -> Option<Chars> {
1632         // Bounds check
1633         if char_idx <= self.len_chars() {
1634             let info = self.root.text_info();
1635             Some(Chars::new_with_range_at(
1636                 &self.root,
1637                 char_idx,
1638                 (0, info.bytes as usize),
1639                 (0, info.chars as usize),
1640                 (0, info.line_breaks as usize + 1),
1641             ))
1642         } else {
1643             None
1644         }
1645     }
1646 
1647     /// Non-panicking version of [`lines_at()`](Rope::lines_at).
1648     #[inline]
get_lines_at(&self, line_idx: usize) -> Option<Lines>1649     pub fn get_lines_at(&self, line_idx: usize) -> Option<Lines> {
1650         // Bounds check
1651         if line_idx <= self.len_lines() {
1652             Some(Lines::new_with_range_at(
1653                 &self.root,
1654                 line_idx,
1655                 (0, self.len_bytes()),
1656                 (0, self.len_lines()),
1657             ))
1658         } else {
1659             None
1660         }
1661     }
1662 
1663     /// Non-panicking version of [`chunks_at_byte()`](Rope::chunks_at_byte).
1664     #[inline]
get_chunks_at_byte(&self, byte_idx: usize) -> Option<(Chunks, usize, usize, usize)>1665     pub fn get_chunks_at_byte(&self, byte_idx: usize) -> Option<(Chunks, usize, usize, usize)> {
1666         // Bounds check
1667         if byte_idx <= self.len_bytes() {
1668             Some(Chunks::new_with_range_at_byte(
1669                 &self.root,
1670                 byte_idx,
1671                 (0, self.len_bytes()),
1672                 (0, self.len_chars()),
1673                 (0, self.len_lines()),
1674             ))
1675         } else {
1676             None
1677         }
1678     }
1679 
1680     /// Non-panicking version of [`chunks_at_char()`](Rope::chunks_at_char).
1681     #[inline]
get_chunks_at_char(&self, char_idx: usize) -> Option<(Chunks, usize, usize, usize)>1682     pub fn get_chunks_at_char(&self, char_idx: usize) -> Option<(Chunks, usize, usize, usize)> {
1683         // Bounds check
1684         if char_idx <= self.len_chars() {
1685             Some(Chunks::new_with_range_at_char(
1686                 &self.root,
1687                 char_idx,
1688                 (0, self.len_bytes()),
1689                 (0, self.len_chars()),
1690                 (0, self.len_lines()),
1691             ))
1692         } else {
1693             None
1694         }
1695     }
1696 
1697     /// Non-panicking version of [`chunks_at_line_break()`](Rope::chunks_at_line_break).
1698     #[inline]
get_chunks_at_line_break( &self, line_break_idx: usize, ) -> Option<(Chunks, usize, usize, usize)>1699     pub fn get_chunks_at_line_break(
1700         &self,
1701         line_break_idx: usize,
1702     ) -> Option<(Chunks, usize, usize, usize)> {
1703         // Bounds check
1704         if line_break_idx <= self.len_lines() {
1705             Some(Chunks::new_with_range_at_line_break(
1706                 &self.root,
1707                 line_break_idx,
1708                 (0, self.len_bytes()),
1709                 (0, self.len_chars()),
1710                 (0, self.len_lines()),
1711             ))
1712         } else {
1713             None
1714         }
1715     }
1716 }
1717 
1718 //==============================================================
1719 // Conversion impls
1720 
1721 impl<'a> From<&'a str> for Rope {
1722     #[inline]
from(text: &'a str) -> Self1723     fn from(text: &'a str) -> Self {
1724         Rope::from_str(text)
1725     }
1726 }
1727 
1728 impl<'a> From<std::borrow::Cow<'a, str>> for Rope {
1729     #[inline]
from(text: std::borrow::Cow<'a, str>) -> Self1730     fn from(text: std::borrow::Cow<'a, str>) -> Self {
1731         Rope::from_str(&text)
1732     }
1733 }
1734 
1735 impl From<String> for Rope {
1736     #[inline]
from(text: String) -> Self1737     fn from(text: String) -> Self {
1738         Rope::from_str(&text)
1739     }
1740 }
1741 
1742 /// Will share data where possible.
1743 ///
1744 /// Runs in O(log N) time.
1745 impl<'a> From<RopeSlice<'a>> for Rope {
from(s: RopeSlice<'a>) -> Self1746     fn from(s: RopeSlice<'a>) -> Self {
1747         use crate::slice::RSEnum;
1748         match s {
1749             RopeSlice(RSEnum::Full {
1750                 node,
1751                 start_info,
1752                 end_info,
1753             }) => {
1754                 let mut rope = Rope {
1755                     root: Arc::clone(node),
1756                 };
1757 
1758                 // Chop off right end if needed
1759                 if end_info.chars < node.text_info().chars {
1760                     {
1761                         let root = Arc::make_mut(&mut rope.root);
1762                         root.split(end_info.chars as usize);
1763                         root.zip_fix_right();
1764                     }
1765                     rope.pull_up_singular_nodes();
1766                 }
1767 
1768                 // Chop off left end if needed
1769                 if start_info.chars > 0 {
1770                     {
1771                         let root = Arc::make_mut(&mut rope.root);
1772                         *root = root.split(start_info.chars as usize);
1773                         root.zip_fix_left();
1774                     }
1775                     rope.pull_up_singular_nodes();
1776                 }
1777 
1778                 // Return the rope
1779                 rope
1780             }
1781             RopeSlice(RSEnum::Light { text, .. }) => Rope::from_str(text),
1782         }
1783     }
1784 }
1785 
1786 impl From<Rope> for String {
1787     #[inline]
from(r: Rope) -> Self1788     fn from(r: Rope) -> Self {
1789         String::from(&r)
1790     }
1791 }
1792 
1793 impl<'a> From<&'a Rope> for String {
1794     #[inline]
from(r: &'a Rope) -> Self1795     fn from(r: &'a Rope) -> Self {
1796         let mut text = String::with_capacity(r.len_bytes());
1797         text.extend(r.chunks());
1798         text
1799     }
1800 }
1801 
1802 impl<'a> From<Rope> for std::borrow::Cow<'a, str> {
1803     #[inline]
from(r: Rope) -> Self1804     fn from(r: Rope) -> Self {
1805         std::borrow::Cow::Owned(String::from(r))
1806     }
1807 }
1808 
1809 /// Attempts to borrow the contents of the `Rope`, but will convert to an
1810 /// owned string if the contents is not contiguous in memory.
1811 ///
1812 /// Runs in best case O(1), worst case O(N).
1813 impl<'a> From<&'a Rope> for std::borrow::Cow<'a, str> {
1814     #[inline]
from(r: &'a Rope) -> Self1815     fn from(r: &'a Rope) -> Self {
1816         if let Node::Leaf(ref text) = *r.root {
1817             std::borrow::Cow::Borrowed(text)
1818         } else {
1819             std::borrow::Cow::Owned(String::from(r))
1820         }
1821     }
1822 }
1823 
1824 impl<'a> FromIterator<&'a str> for Rope {
from_iter<T>(iter: T) -> Self where T: IntoIterator<Item = &'a str>,1825     fn from_iter<T>(iter: T) -> Self
1826     where
1827         T: IntoIterator<Item = &'a str>,
1828     {
1829         let mut builder = RopeBuilder::new();
1830         for chunk in iter {
1831             builder.append(chunk);
1832         }
1833         builder.finish()
1834     }
1835 }
1836 
1837 impl<'a> FromIterator<std::borrow::Cow<'a, str>> for Rope {
from_iter<T>(iter: T) -> Self where T: IntoIterator<Item = std::borrow::Cow<'a, str>>,1838     fn from_iter<T>(iter: T) -> Self
1839     where
1840         T: IntoIterator<Item = std::borrow::Cow<'a, str>>,
1841     {
1842         let mut builder = RopeBuilder::new();
1843         for chunk in iter {
1844             builder.append(&chunk);
1845         }
1846         builder.finish()
1847     }
1848 }
1849 
1850 impl FromIterator<String> for Rope {
from_iter<T>(iter: T) -> Self where T: IntoIterator<Item = String>,1851     fn from_iter<T>(iter: T) -> Self
1852     where
1853         T: IntoIterator<Item = String>,
1854     {
1855         let mut builder = RopeBuilder::new();
1856         for chunk in iter {
1857             builder.append(&chunk);
1858         }
1859         builder.finish()
1860     }
1861 }
1862 
1863 //==============================================================
1864 // Other impls
1865 
1866 impl std::fmt::Debug for Rope {
fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result1867     fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
1868         f.debug_list().entries(self.chunks()).finish()
1869     }
1870 }
1871 
1872 impl std::fmt::Display for Rope {
1873     #[inline]
fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result1874     fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
1875         for chunk in self.chunks() {
1876             write!(f, "{}", chunk)?
1877         }
1878         Ok(())
1879     }
1880 }
1881 
1882 impl std::default::Default for Rope {
1883     #[inline]
default() -> Self1884     fn default() -> Self {
1885         Self::new()
1886     }
1887 }
1888 
1889 impl std::cmp::Eq for Rope {}
1890 
1891 impl std::cmp::PartialEq<Rope> for Rope {
1892     #[inline]
eq(&self, other: &Rope) -> bool1893     fn eq(&self, other: &Rope) -> bool {
1894         self.slice(..) == other.slice(..)
1895     }
1896 }
1897 
1898 impl<'a> std::cmp::PartialEq<&'a str> for Rope {
1899     #[inline]
eq(&self, other: &&'a str) -> bool1900     fn eq(&self, other: &&'a str) -> bool {
1901         self.slice(..) == *other
1902     }
1903 }
1904 
1905 impl<'a> std::cmp::PartialEq<Rope> for &'a str {
1906     #[inline]
eq(&self, other: &Rope) -> bool1907     fn eq(&self, other: &Rope) -> bool {
1908         *self == other.slice(..)
1909     }
1910 }
1911 
1912 impl std::cmp::PartialEq<str> for Rope {
1913     #[inline]
eq(&self, other: &str) -> bool1914     fn eq(&self, other: &str) -> bool {
1915         self.slice(..) == other
1916     }
1917 }
1918 
1919 impl std::cmp::PartialEq<Rope> for str {
1920     #[inline]
eq(&self, other: &Rope) -> bool1921     fn eq(&self, other: &Rope) -> bool {
1922         self == other.slice(..)
1923     }
1924 }
1925 
1926 impl<'a> std::cmp::PartialEq<String> for Rope {
1927     #[inline]
eq(&self, other: &String) -> bool1928     fn eq(&self, other: &String) -> bool {
1929         self.slice(..) == other.as_str()
1930     }
1931 }
1932 
1933 impl<'a> std::cmp::PartialEq<Rope> for String {
1934     #[inline]
eq(&self, other: &Rope) -> bool1935     fn eq(&self, other: &Rope) -> bool {
1936         self.as_str() == other.slice(..)
1937     }
1938 }
1939 
1940 impl<'a> std::cmp::PartialEq<std::borrow::Cow<'a, str>> for Rope {
1941     #[inline]
eq(&self, other: &std::borrow::Cow<'a, str>) -> bool1942     fn eq(&self, other: &std::borrow::Cow<'a, str>) -> bool {
1943         self.slice(..) == **other
1944     }
1945 }
1946 
1947 impl<'a> std::cmp::PartialEq<Rope> for std::borrow::Cow<'a, str> {
1948     #[inline]
eq(&self, other: &Rope) -> bool1949     fn eq(&self, other: &Rope) -> bool {
1950         **self == other.slice(..)
1951     }
1952 }
1953 
1954 impl std::cmp::Ord for Rope {
1955     #[inline]
cmp(&self, other: &Rope) -> std::cmp::Ordering1956     fn cmp(&self, other: &Rope) -> std::cmp::Ordering {
1957         self.slice(..).cmp(&other.slice(..))
1958     }
1959 }
1960 
1961 impl std::cmp::PartialOrd<Rope> for Rope {
1962     #[inline]
partial_cmp(&self, other: &Rope) -> Option<std::cmp::Ordering>1963     fn partial_cmp(&self, other: &Rope) -> Option<std::cmp::Ordering> {
1964         Some(self.cmp(other))
1965     }
1966 }
1967 
1968 //==============================================================
1969 
1970 #[cfg(test)]
1971 mod tests {
1972     use super::*;
1973     use crate::str_utils::byte_to_char_idx;
1974 
1975     // 127 bytes, 103 chars, 1 line
1976     const TEXT: &str = "Hello there!  How're you doing?  It's \
1977                         a fine day, isn't it?  Aren't you glad \
1978                         we're alive?  こんにちは、みんなさん!";
1979     // 124 bytes, 100 chars, 4 lines
1980     const TEXT_LINES: &str = "Hello there!  How're you doing?\nIt's \
1981                               a fine day, isn't it?\nAren't you glad \
1982                               we're alive?\nこんにちは、みんなさん!";
1983     // 127 bytes, 107 chars, 111 utf16 code units, 1 line
1984     const TEXT_EMOJI: &str = "Hello there!��  How're you doing?��  It's \
1985                               a fine day, isn't it?��  Aren't you glad \
1986                               we're alive?��  こんにちは、みんなさん!";
1987 
1988     #[test]
new_01()1989     fn new_01() {
1990         let r = Rope::new();
1991         assert_eq!(r, "");
1992 
1993         r.assert_integrity();
1994         r.assert_invariants();
1995     }
1996 
1997     #[test]
from_str()1998     fn from_str() {
1999         let r = Rope::from_str(TEXT);
2000         assert_eq!(r, TEXT);
2001 
2002         r.assert_integrity();
2003         r.assert_invariants();
2004     }
2005 
2006     #[test]
len_bytes_01()2007     fn len_bytes_01() {
2008         let r = Rope::from_str(TEXT);
2009         assert_eq!(r.len_bytes(), 127);
2010     }
2011 
2012     #[test]
len_bytes_02()2013     fn len_bytes_02() {
2014         let r = Rope::from_str("");
2015         assert_eq!(r.len_bytes(), 0);
2016     }
2017 
2018     #[test]
len_chars_01()2019     fn len_chars_01() {
2020         let r = Rope::from_str(TEXT);
2021         assert_eq!(r.len_chars(), 103);
2022     }
2023 
2024     #[test]
len_chars_02()2025     fn len_chars_02() {
2026         let r = Rope::from_str("");
2027         assert_eq!(r.len_chars(), 0);
2028     }
2029 
2030     #[test]
len_lines_01()2031     fn len_lines_01() {
2032         let r = Rope::from_str(TEXT_LINES);
2033         assert_eq!(r.len_lines(), 4);
2034     }
2035 
2036     #[test]
len_lines_02()2037     fn len_lines_02() {
2038         let r = Rope::from_str("");
2039         assert_eq!(r.len_lines(), 1);
2040     }
2041 
2042     #[test]
len_utf16_cu_01()2043     fn len_utf16_cu_01() {
2044         let r = Rope::from_str(TEXT);
2045         assert_eq!(r.len_utf16_cu(), 103);
2046     }
2047 
2048     #[test]
len_utf16_cu_02()2049     fn len_utf16_cu_02() {
2050         let r = Rope::from_str(TEXT_EMOJI);
2051         assert_eq!(r.len_utf16_cu(), 111);
2052     }
2053 
2054     #[test]
len_utf16_cu_03()2055     fn len_utf16_cu_03() {
2056         let r = Rope::from_str("");
2057         assert_eq!(r.len_utf16_cu(), 0);
2058     }
2059 
2060     #[test]
insert_01()2061     fn insert_01() {
2062         let mut r = Rope::from_str(TEXT);
2063         r.insert(3, "AA");
2064 
2065         assert_eq!(
2066             r,
2067             "HelAAlo there!  How're you doing?  It's \
2068              a fine day, isn't it?  Aren't you glad \
2069              we're alive?  こんにちは、みんなさん!"
2070         );
2071 
2072         r.assert_integrity();
2073         r.assert_invariants();
2074     }
2075 
2076     #[test]
insert_02()2077     fn insert_02() {
2078         let mut r = Rope::from_str(TEXT);
2079         r.insert(0, "AA");
2080 
2081         assert_eq!(
2082             r,
2083             "AAHello there!  How're you doing?  It's \
2084              a fine day, isn't it?  Aren't you glad \
2085              we're alive?  こんにちは、みんなさん!"
2086         );
2087 
2088         r.assert_integrity();
2089         r.assert_invariants();
2090     }
2091 
2092     #[test]
insert_03()2093     fn insert_03() {
2094         let mut r = Rope::from_str(TEXT);
2095         r.insert(103, "AA");
2096 
2097         assert_eq!(
2098             r,
2099             "Hello there!  How're you doing?  It's \
2100              a fine day, isn't it?  Aren't you glad \
2101              we're alive?  こんにちは、みんなさん!AA"
2102         );
2103 
2104         r.assert_integrity();
2105         r.assert_invariants();
2106     }
2107 
2108     #[test]
insert_04()2109     fn insert_04() {
2110         let mut r = Rope::new();
2111         r.insert(0, "He");
2112         r.insert(2, "l");
2113         r.insert(3, "l");
2114         r.insert(4, "o w");
2115         r.insert(7, "o");
2116         r.insert(8, "rl");
2117         r.insert(10, "d!");
2118         r.insert(3, "zopter");
2119 
2120         assert_eq!("Helzopterlo world!", r);
2121 
2122         r.assert_integrity();
2123         r.assert_invariants();
2124     }
2125 
2126     #[test]
insert_05()2127     fn insert_05() {
2128         let mut r = Rope::new();
2129         r.insert(0, "こんいちは、みんなさん!");
2130         r.insert(7, "zopter");
2131         assert_eq!("こんいちは、みzopterんなさん!", r);
2132 
2133         r.assert_integrity();
2134         r.assert_invariants();
2135     }
2136 
2137     #[test]
insert_06()2138     fn insert_06() {
2139         let mut r = Rope::new();
2140         r.insert(0, "こ");
2141         r.insert(1, "ん");
2142         r.insert(2, "い");
2143         r.insert(3, "ち");
2144         r.insert(4, "は");
2145         r.insert(5, "、");
2146         r.insert(6, "み");
2147         r.insert(7, "ん");
2148         r.insert(8, "な");
2149         r.insert(9, "さ");
2150         r.insert(10, "ん");
2151         r.insert(11, "!");
2152         r.insert(7, "zopter");
2153         assert_eq!("こんいちは、みzopterんなさん!", r);
2154 
2155         r.assert_integrity();
2156         r.assert_invariants();
2157     }
2158 
2159     #[test]
insert_char_01()2160     fn insert_char_01() {
2161         let mut r = Rope::from_str(TEXT);
2162         r.insert_char(3, 'A');
2163         r.insert_char(12, '!');
2164         r.insert_char(12, '!');
2165 
2166         assert_eq!(
2167             r,
2168             "HelAlo there!!!  How're you doing?  It's \
2169              a fine day, isn't it?  Aren't you glad \
2170              we're alive?  こんにちは、みんなさん!"
2171         );
2172 
2173         r.assert_integrity();
2174         r.assert_invariants();
2175     }
2176 
2177     #[test]
insert_char_02()2178     fn insert_char_02() {
2179         let mut r = Rope::new();
2180 
2181         r.insert_char(0, '!');
2182         r.insert_char(0, 'こ');
2183         r.insert_char(1, 'ん');
2184         r.insert_char(2, 'い');
2185         r.insert_char(3, 'ち');
2186         r.insert_char(4, 'は');
2187         r.insert_char(5, '、');
2188         r.insert_char(6, 'み');
2189         r.insert_char(7, 'ん');
2190         r.insert_char(8, 'な');
2191         r.insert_char(9, 'さ');
2192         r.insert_char(10, 'ん');
2193         assert_eq!("こんいちは、みんなさん!", r);
2194 
2195         r.assert_integrity();
2196         r.assert_invariants();
2197     }
2198 
2199     #[test]
remove_01()2200     fn remove_01() {
2201         let mut r = Rope::from_str(TEXT);
2202 
2203         r.remove(5..11);
2204         r.remove(24..31);
2205         r.remove(19..25);
2206         r.remove(75..79);
2207         assert_eq!(
2208             r,
2209             "Hello!  How're you \
2210              a fine day, isn't it?  Aren't you glad \
2211              we're alive?  こんにんなさん!"
2212         );
2213 
2214         r.assert_integrity();
2215         r.assert_invariants();
2216     }
2217 
2218     #[test]
remove_02()2219     fn remove_02() {
2220         let mut r = Rope::from_str("\r\n\r\n\r\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n");
2221 
2222         // Make sure CRLF pairs get merged properly, via
2223         // assert_invariants() below.
2224         r.remove(3..6);
2225         assert_eq!(r, "\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n");
2226 
2227         r.assert_integrity();
2228         r.assert_invariants();
2229     }
2230 
2231     #[test]
remove_03()2232     fn remove_03() {
2233         let mut r = Rope::from_str(TEXT);
2234 
2235         // Make sure removing nothing actually does nothing.
2236         r.remove(45..45);
2237         assert_eq!(r, TEXT);
2238 
2239         r.assert_integrity();
2240         r.assert_invariants();
2241     }
2242 
2243     #[test]
remove_04()2244     fn remove_04() {
2245         let mut r = Rope::from_str(TEXT);
2246 
2247         // Make sure removing everything works.
2248         r.remove(0..103);
2249         assert_eq!(r, "");
2250 
2251         r.assert_integrity();
2252         r.assert_invariants();
2253     }
2254 
2255     #[test]
remove_05()2256     fn remove_05() {
2257         let mut r = Rope::from_str(TEXT);
2258 
2259         // Make sure removing a large range works.
2260         r.remove(3..100);
2261         assert_eq!(r, "Helさん!");
2262 
2263         r.assert_integrity();
2264         r.assert_invariants();
2265     }
2266 
2267     #[test]
2268     #[should_panic]
remove_06()2269     fn remove_06() {
2270         let mut r = Rope::from_str(TEXT);
2271         r.remove(56..55); // Wrong ordering of start/end
2272     }
2273 
2274     #[test]
2275     #[should_panic]
remove_07()2276     fn remove_07() {
2277         let mut r = Rope::from_str(TEXT);
2278         r.remove(102..104); // Removing past the end
2279     }
2280 
2281     #[test]
2282     #[should_panic]
remove_08()2283     fn remove_08() {
2284         let mut r = Rope::from_str(TEXT);
2285         r.remove(103..104); // Removing past the end
2286     }
2287 
2288     #[test]
2289     #[should_panic]
remove_09()2290     fn remove_09() {
2291         let mut r = Rope::from_str(TEXT);
2292         r.remove(104..104); // Removing past the end
2293     }
2294 
2295     #[test]
2296     #[should_panic]
remove_10()2297     fn remove_10() {
2298         let mut r = Rope::from_str(TEXT);
2299         r.remove(104..105); // Removing past the end
2300     }
2301 
2302     #[test]
split_off_01()2303     fn split_off_01() {
2304         let mut r = Rope::from_str(TEXT);
2305 
2306         let r2 = r.split_off(50);
2307         assert_eq!(
2308             r,
2309             "Hello there!  How're you doing?  It's \
2310              a fine day, "
2311         );
2312         assert_eq!(
2313             r2,
2314             "isn't it?  Aren't you glad \
2315              we're alive?  こんにちは、みんなさん!"
2316         );
2317 
2318         r.assert_integrity();
2319         r2.assert_integrity();
2320         r.assert_invariants();
2321         r2.assert_invariants();
2322     }
2323 
2324     #[test]
split_off_02()2325     fn split_off_02() {
2326         let mut r = Rope::from_str(TEXT);
2327 
2328         let r2 = r.split_off(1);
2329         assert_eq!(r, "H");
2330         assert_eq!(
2331             r2,
2332             "ello there!  How're you doing?  It's \
2333              a fine day, isn't it?  Aren't you glad \
2334              we're alive?  こんにちは、みんなさん!"
2335         );
2336 
2337         r.assert_integrity();
2338         r2.assert_integrity();
2339         r.assert_invariants();
2340         r2.assert_invariants();
2341     }
2342 
2343     #[test]
split_off_03()2344     fn split_off_03() {
2345         let mut r = Rope::from_str(TEXT);
2346 
2347         let r2 = r.split_off(102);
2348         assert_eq!(
2349             r,
2350             "Hello there!  How're you doing?  It's \
2351              a fine day, isn't it?  Aren't you glad \
2352              we're alive?  こんにちは、みんなさん"
2353         );
2354         assert_eq!(r2, "!");
2355 
2356         r.assert_integrity();
2357         r2.assert_integrity();
2358         r.assert_invariants();
2359         r2.assert_invariants();
2360     }
2361 
2362     #[test]
split_off_04()2363     fn split_off_04() {
2364         let mut r = Rope::from_str(TEXT);
2365 
2366         let r2 = r.split_off(0);
2367         assert_eq!(r, "");
2368         assert_eq!(
2369             r2,
2370             "Hello there!  How're you doing?  It's \
2371              a fine day, isn't it?  Aren't you glad \
2372              we're alive?  こんにちは、みんなさん!"
2373         );
2374 
2375         r.assert_integrity();
2376         r2.assert_integrity();
2377         r.assert_invariants();
2378         r2.assert_invariants();
2379     }
2380 
2381     #[test]
split_off_05()2382     fn split_off_05() {
2383         let mut r = Rope::from_str(TEXT);
2384 
2385         let r2 = r.split_off(103);
2386         assert_eq!(
2387             r,
2388             "Hello there!  How're you doing?  It's \
2389              a fine day, isn't it?  Aren't you glad \
2390              we're alive?  こんにちは、みんなさん!"
2391         );
2392         assert_eq!(r2, "");
2393 
2394         r.assert_integrity();
2395         r2.assert_integrity();
2396         r.assert_invariants();
2397         r2.assert_invariants();
2398     }
2399 
2400     #[test]
2401     #[should_panic]
split_off_06()2402     fn split_off_06() {
2403         let mut r = Rope::from_str(TEXT);
2404         r.split_off(104); // One past the end of the rope
2405     }
2406 
2407     #[test]
append_01()2408     fn append_01() {
2409         let mut r = Rope::from_str(
2410             "Hello there!  How're you doing?  It's \
2411              a fine day, isn't ",
2412         );
2413         let r2 = Rope::from_str(
2414             "it?  Aren't you glad \
2415              we're alive?  こんにちは、みんなさん!",
2416         );
2417 
2418         r.append(r2);
2419         assert_eq!(r, TEXT);
2420 
2421         r.assert_integrity();
2422         r.assert_invariants();
2423     }
2424 
2425     #[test]
append_02()2426     fn append_02() {
2427         let mut r = Rope::from_str(
2428             "Hello there!  How're you doing?  It's \
2429              a fine day, isn't it?  Aren't you glad \
2430              we're alive?  こんに",
2431         );
2432         let r2 = Rope::from_str("ちは、みんなさん!");
2433 
2434         r.append(r2);
2435         assert_eq!(r, TEXT);
2436 
2437         r.assert_integrity();
2438         r.assert_invariants();
2439     }
2440 
2441     #[test]
append_03()2442     fn append_03() {
2443         let mut r = Rope::from_str(
2444             "Hello there!  How're you doing?  It's \
2445              a fine day, isn't it?  Aren't you glad \
2446              we're alive?  こんにちは、みんなさん",
2447         );
2448         let r2 = Rope::from_str("!");
2449 
2450         r.append(r2);
2451         assert_eq!(r, TEXT);
2452 
2453         r.assert_integrity();
2454         r.assert_invariants();
2455     }
2456 
2457     #[test]
append_04()2458     fn append_04() {
2459         let mut r = Rope::from_str("H");
2460         let r2 = Rope::from_str(
2461             "ello there!  How're you doing?  It's \
2462              a fine day, isn't it?  Aren't you glad \
2463              we're alive?  こんにちは、みんなさん!",
2464         );
2465 
2466         r.append(r2);
2467         assert_eq!(r, TEXT);
2468 
2469         r.assert_integrity();
2470         r.assert_invariants();
2471     }
2472 
2473     #[test]
append_05()2474     fn append_05() {
2475         let mut r = Rope::from_str(TEXT);
2476         let r2 = Rope::from_str("");
2477 
2478         r.append(r2);
2479         assert_eq!(r, TEXT);
2480 
2481         r.assert_integrity();
2482         r.assert_invariants();
2483     }
2484 
2485     #[test]
append_06()2486     fn append_06() {
2487         let mut r = Rope::from_str("");
2488         let r2 = Rope::from_str(TEXT);
2489 
2490         r.append(r2);
2491         assert_eq!(r, TEXT);
2492 
2493         r.assert_integrity();
2494         r.assert_invariants();
2495     }
2496 
2497     #[test]
append_07()2498     fn append_07() {
2499         let mut r = Rope::from_str("\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r");
2500         let r2 = Rope::from_str("\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r");
2501 
2502         r.append(r2);
2503         assert_eq!(r, "\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r\n\r");
2504         assert_eq!(r.len_lines(), 24);
2505 
2506         r.assert_integrity();
2507         r.assert_invariants();
2508     }
2509 
2510     #[test]
shrink_to_fit_01()2511     fn shrink_to_fit_01() {
2512         let mut r = Rope::new();
2513         for _ in 0..10 {
2514             let len = r.len_chars();
2515             r.insert(len / 2, "こ");
2516             r.insert(len / 2, "ん");
2517             r.insert(len / 2, "い");
2518             r.insert(len / 2, "ち");
2519             r.insert(len / 2, "は");
2520             r.insert(len / 2, "、");
2521             r.insert(len / 2, "み");
2522             r.insert(len / 2, "ん");
2523             r.insert(len / 2, "な");
2524             r.insert(len / 2, "さ");
2525             r.insert(len / 2, "ん");
2526             r.insert(len / 2, "!");
2527             r.insert(len / 2, "zopter");
2528         }
2529 
2530         let r2 = r.clone();
2531         r.shrink_to_fit();
2532 
2533         assert_eq!(r, r2);
2534 
2535         r.assert_integrity();
2536         r.assert_invariants();
2537     }
2538 
2539     #[test]
byte_to_char_01()2540     fn byte_to_char_01() {
2541         let r = Rope::from_str(TEXT);
2542 
2543         assert_eq!(0, r.byte_to_char(0));
2544         assert_eq!(1, r.byte_to_char(1));
2545         assert_eq!(2, r.byte_to_char(2));
2546 
2547         assert_eq!(91, r.byte_to_char(91));
2548         assert_eq!(91, r.byte_to_char(92));
2549         assert_eq!(91, r.byte_to_char(93));
2550 
2551         assert_eq!(92, r.byte_to_char(94));
2552         assert_eq!(92, r.byte_to_char(95));
2553         assert_eq!(92, r.byte_to_char(96));
2554 
2555         assert_eq!(102, r.byte_to_char(124));
2556         assert_eq!(102, r.byte_to_char(125));
2557         assert_eq!(102, r.byte_to_char(126));
2558         assert_eq!(103, r.byte_to_char(127));
2559     }
2560 
2561     #[test]
byte_to_line_01()2562     fn byte_to_line_01() {
2563         let r = Rope::from_str(TEXT_LINES);
2564 
2565         assert_eq!(0, r.byte_to_line(0));
2566         assert_eq!(0, r.byte_to_line(1));
2567 
2568         assert_eq!(0, r.byte_to_line(31));
2569         assert_eq!(1, r.byte_to_line(32));
2570         assert_eq!(1, r.byte_to_line(33));
2571 
2572         assert_eq!(1, r.byte_to_line(58));
2573         assert_eq!(2, r.byte_to_line(59));
2574         assert_eq!(2, r.byte_to_line(60));
2575 
2576         assert_eq!(2, r.byte_to_line(87));
2577         assert_eq!(3, r.byte_to_line(88));
2578         assert_eq!(3, r.byte_to_line(89));
2579         assert_eq!(3, r.byte_to_line(124));
2580     }
2581 
2582     #[test]
byte_to_line_02()2583     fn byte_to_line_02() {
2584         let r = Rope::from_str("");
2585         assert_eq!(0, r.byte_to_line(0));
2586     }
2587 
2588     #[test]
byte_to_line_03()2589     fn byte_to_line_03() {
2590         let r = Rope::from_str("Hi there\n");
2591         assert_eq!(0, r.byte_to_line(0));
2592         assert_eq!(0, r.byte_to_line(8));
2593         assert_eq!(1, r.byte_to_line(9));
2594     }
2595 
2596     #[test]
2597     #[should_panic]
byte_to_line_04()2598     fn byte_to_line_04() {
2599         let r = Rope::from_str(TEXT_LINES);
2600         r.byte_to_line(125);
2601     }
2602 
2603     #[test]
char_to_byte_01()2604     fn char_to_byte_01() {
2605         let r = Rope::from_str(TEXT);
2606 
2607         assert_eq!(0, r.char_to_byte(0));
2608         assert_eq!(1, r.char_to_byte(1));
2609         assert_eq!(2, r.char_to_byte(2));
2610 
2611         assert_eq!(91, r.char_to_byte(91));
2612         assert_eq!(94, r.char_to_byte(92));
2613         assert_eq!(97, r.char_to_byte(93));
2614         assert_eq!(100, r.char_to_byte(94));
2615 
2616         assert_eq!(124, r.char_to_byte(102));
2617         assert_eq!(127, r.char_to_byte(103));
2618     }
2619 
2620     #[test]
char_to_line_01()2621     fn char_to_line_01() {
2622         let r = Rope::from_str(TEXT_LINES);
2623 
2624         assert_eq!(0, r.char_to_line(0));
2625         assert_eq!(0, r.char_to_line(1));
2626 
2627         assert_eq!(0, r.char_to_line(31));
2628         assert_eq!(1, r.char_to_line(32));
2629         assert_eq!(1, r.char_to_line(33));
2630 
2631         assert_eq!(1, r.char_to_line(58));
2632         assert_eq!(2, r.char_to_line(59));
2633         assert_eq!(2, r.char_to_line(60));
2634 
2635         assert_eq!(2, r.char_to_line(87));
2636         assert_eq!(3, r.char_to_line(88));
2637         assert_eq!(3, r.char_to_line(89));
2638         assert_eq!(3, r.char_to_line(100));
2639     }
2640 
2641     #[test]
char_to_line_02()2642     fn char_to_line_02() {
2643         let r = Rope::from_str("");
2644         assert_eq!(0, r.char_to_line(0));
2645     }
2646 
2647     #[test]
char_to_line_03()2648     fn char_to_line_03() {
2649         let r = Rope::from_str("Hi there\n");
2650         assert_eq!(0, r.char_to_line(0));
2651         assert_eq!(0, r.char_to_line(8));
2652         assert_eq!(1, r.char_to_line(9));
2653     }
2654 
2655     #[test]
2656     #[should_panic]
char_to_line_04()2657     fn char_to_line_04() {
2658         let r = Rope::from_str(TEXT_LINES);
2659         r.char_to_line(101);
2660     }
2661 
2662     #[test]
line_to_byte_01()2663     fn line_to_byte_01() {
2664         let r = Rope::from_str(TEXT_LINES);
2665 
2666         assert_eq!(0, r.line_to_byte(0));
2667         assert_eq!(32, r.line_to_byte(1));
2668         assert_eq!(59, r.line_to_byte(2));
2669         assert_eq!(88, r.line_to_byte(3));
2670         assert_eq!(124, r.line_to_byte(4));
2671     }
2672 
2673     #[test]
line_to_byte_02()2674     fn line_to_byte_02() {
2675         let r = Rope::from_str("");
2676         assert_eq!(0, r.line_to_byte(0));
2677         assert_eq!(0, r.line_to_byte(1));
2678     }
2679 
2680     #[test]
2681     #[should_panic]
line_to_byte_03()2682     fn line_to_byte_03() {
2683         let r = Rope::from_str(TEXT_LINES);
2684         r.line_to_byte(5);
2685     }
2686 
2687     #[test]
line_to_char_01()2688     fn line_to_char_01() {
2689         let r = Rope::from_str(TEXT_LINES);
2690 
2691         assert_eq!(0, r.line_to_char(0));
2692         assert_eq!(32, r.line_to_char(1));
2693         assert_eq!(59, r.line_to_char(2));
2694         assert_eq!(88, r.line_to_char(3));
2695         assert_eq!(100, r.line_to_char(4));
2696     }
2697 
2698     #[test]
line_to_char_02()2699     fn line_to_char_02() {
2700         let r = Rope::from_str("");
2701         assert_eq!(0, r.line_to_char(0));
2702         assert_eq!(0, r.line_to_char(1));
2703     }
2704 
2705     #[test]
2706     #[should_panic]
line_to_char_03()2707     fn line_to_char_03() {
2708         let r = Rope::from_str(TEXT_LINES);
2709         r.line_to_char(5);
2710     }
2711 
2712     #[test]
char_to_utf16_cu_01()2713     fn char_to_utf16_cu_01() {
2714         let r = Rope::from_str("");
2715         assert_eq!(0, r.char_to_utf16_cu(0));
2716     }
2717 
2718     #[test]
2719     #[should_panic]
char_to_utf16_cu_02()2720     fn char_to_utf16_cu_02() {
2721         let r = Rope::from_str("");
2722         r.char_to_utf16_cu(1);
2723     }
2724 
2725     #[test]
char_to_utf16_cu_03()2726     fn char_to_utf16_cu_03() {
2727         let r = Rope::from_str(TEXT_EMOJI);
2728 
2729         assert_eq!(0, r.char_to_utf16_cu(0));
2730 
2731         assert_eq!(12, r.char_to_utf16_cu(12));
2732         assert_eq!(14, r.char_to_utf16_cu(13));
2733 
2734         assert_eq!(33, r.char_to_utf16_cu(32));
2735         assert_eq!(35, r.char_to_utf16_cu(33));
2736 
2737         assert_eq!(63, r.char_to_utf16_cu(61));
2738         assert_eq!(65, r.char_to_utf16_cu(62));
2739 
2740         assert_eq!(95, r.char_to_utf16_cu(92));
2741         assert_eq!(97, r.char_to_utf16_cu(93));
2742 
2743         assert_eq!(111, r.char_to_utf16_cu(107));
2744     }
2745 
2746     #[test]
2747     #[should_panic]
char_to_utf16_cu_04()2748     fn char_to_utf16_cu_04() {
2749         let r = Rope::from_str(TEXT_EMOJI);
2750         r.char_to_utf16_cu(108);
2751     }
2752 
2753     #[test]
utf16_cu_to_char_01()2754     fn utf16_cu_to_char_01() {
2755         let r = Rope::from_str("");
2756         assert_eq!(0, r.utf16_cu_to_char(0));
2757     }
2758 
2759     #[test]
2760     #[should_panic]
utf16_cu_to_char_02()2761     fn utf16_cu_to_char_02() {
2762         let r = Rope::from_str("");
2763         r.utf16_cu_to_char(1);
2764     }
2765 
2766     #[test]
utf16_cu_to_char_03()2767     fn utf16_cu_to_char_03() {
2768         let r = Rope::from_str(TEXT_EMOJI);
2769 
2770         assert_eq!(0, r.utf16_cu_to_char(0));
2771 
2772         assert_eq!(12, r.utf16_cu_to_char(12));
2773         assert_eq!(12, r.utf16_cu_to_char(13));
2774         assert_eq!(13, r.utf16_cu_to_char(14));
2775 
2776         assert_eq!(32, r.utf16_cu_to_char(33));
2777         assert_eq!(32, r.utf16_cu_to_char(34));
2778         assert_eq!(33, r.utf16_cu_to_char(35));
2779 
2780         assert_eq!(61, r.utf16_cu_to_char(63));
2781         assert_eq!(61, r.utf16_cu_to_char(64));
2782         assert_eq!(62, r.utf16_cu_to_char(65));
2783 
2784         assert_eq!(92, r.utf16_cu_to_char(95));
2785         assert_eq!(92, r.utf16_cu_to_char(96));
2786         assert_eq!(93, r.utf16_cu_to_char(97));
2787 
2788         assert_eq!(107, r.utf16_cu_to_char(111));
2789     }
2790 
2791     #[test]
2792     #[should_panic]
utf16_cu_to_char_04()2793     fn utf16_cu_to_char_04() {
2794         let r = Rope::from_str(TEXT_EMOJI);
2795         r.utf16_cu_to_char(112);
2796     }
2797 
2798     #[test]
byte_01()2799     fn byte_01() {
2800         let r = Rope::from_str(TEXT);
2801 
2802         assert_eq!(r.byte(0), b'H');
2803 
2804         // UTF-8 for "wide exclamation mark"
2805         assert_eq!(r.byte(124), 0xEF);
2806         assert_eq!(r.byte(125), 0xBC);
2807         assert_eq!(r.byte(126), 0x81);
2808     }
2809 
2810     #[test]
2811     #[should_panic]
byte_02()2812     fn byte_02() {
2813         let r = Rope::from_str(TEXT);
2814         r.byte(127);
2815     }
2816 
2817     #[test]
2818     #[should_panic]
byte_03()2819     fn byte_03() {
2820         let r = Rope::from_str("");
2821         r.byte(0);
2822     }
2823 
2824     #[test]
char_01()2825     fn char_01() {
2826         let r = Rope::from_str(TEXT);
2827 
2828         assert_eq!(r.char(0), 'H');
2829         assert_eq!(r.char(10), 'e');
2830         assert_eq!(r.char(18), 'r');
2831         assert_eq!(r.char(102), '!');
2832     }
2833 
2834     #[test]
2835     #[should_panic]
char_02()2836     fn char_02() {
2837         let r = Rope::from_str(TEXT);
2838         r.char(103);
2839     }
2840 
2841     #[test]
2842     #[should_panic]
char_03()2843     fn char_03() {
2844         let r = Rope::from_str("");
2845         r.char(0);
2846     }
2847 
2848     #[test]
line_01()2849     fn line_01() {
2850         let r = Rope::from_str(TEXT_LINES);
2851 
2852         let l0 = r.line(0);
2853         assert_eq!(l0, "Hello there!  How're you doing?\n");
2854         assert_eq!(l0.len_bytes(), 32);
2855         assert_eq!(l0.len_chars(), 32);
2856         assert_eq!(l0.len_lines(), 2);
2857 
2858         let l1 = r.line(1);
2859         assert_eq!(l1, "It's a fine day, isn't it?\n");
2860         assert_eq!(l1.len_bytes(), 27);
2861         assert_eq!(l1.len_chars(), 27);
2862         assert_eq!(l1.len_lines(), 2);
2863 
2864         let l2 = r.line(2);
2865         assert_eq!(l2, "Aren't you glad we're alive?\n");
2866         assert_eq!(l2.len_bytes(), 29);
2867         assert_eq!(l2.len_chars(), 29);
2868         assert_eq!(l2.len_lines(), 2);
2869 
2870         let l3 = r.line(3);
2871         assert_eq!(l3, "こんにちは、みんなさん!");
2872         assert_eq!(l3.len_bytes(), 36);
2873         assert_eq!(l3.len_chars(), 12);
2874         assert_eq!(l3.len_lines(), 1);
2875     }
2876 
2877     #[test]
line_02()2878     fn line_02() {
2879         let r = Rope::from_str("Hello there!  How're you doing?\n");
2880 
2881         assert_eq!(r.line(0), "Hello there!  How're you doing?\n");
2882         assert_eq!(r.line(1), "");
2883     }
2884 
2885     #[test]
line_03()2886     fn line_03() {
2887         let r = Rope::from_str("Hi\nHi\nHi\nHi\nHi\nHi\n");
2888 
2889         assert_eq!(r.line(0), "Hi\n");
2890         assert_eq!(r.line(1), "Hi\n");
2891         assert_eq!(r.line(2), "Hi\n");
2892         assert_eq!(r.line(3), "Hi\n");
2893         assert_eq!(r.line(4), "Hi\n");
2894         assert_eq!(r.line(5), "Hi\n");
2895         assert_eq!(r.line(6), "");
2896     }
2897 
2898     #[test]
line_04()2899     fn line_04() {
2900         let r = Rope::from_str("");
2901 
2902         assert_eq!(r.line(0), "");
2903     }
2904 
2905     #[test]
2906     #[should_panic]
line_05()2907     fn line_05() {
2908         let r = Rope::from_str(TEXT_LINES);
2909         r.line(4);
2910     }
2911 
2912     #[test]
line_06()2913     fn line_06() {
2914         let r = Rope::from_str("1\n2\n3\n4\n5\n6\n7\n8");
2915 
2916         assert_eq!(r.line(0).len_lines(), 2);
2917         assert_eq!(r.line(1).len_lines(), 2);
2918         assert_eq!(r.line(2).len_lines(), 2);
2919         assert_eq!(r.line(3).len_lines(), 2);
2920         assert_eq!(r.line(4).len_lines(), 2);
2921         assert_eq!(r.line(5).len_lines(), 2);
2922         assert_eq!(r.line(6).len_lines(), 2);
2923         assert_eq!(r.line(7).len_lines(), 1);
2924     }
2925 
2926     #[test]
chunk_at_byte()2927     fn chunk_at_byte() {
2928         let r = Rope::from_str(TEXT_LINES);
2929         let mut t = TEXT_LINES;
2930 
2931         let mut last_chunk = "";
2932         for i in 0..r.len_bytes() {
2933             let (chunk, b, c, l) = r.chunk_at_byte(i);
2934             assert_eq!(c, byte_to_char_idx(TEXT_LINES, b));
2935             assert_eq!(l, byte_to_line_idx(TEXT_LINES, b));
2936             if chunk != last_chunk {
2937                 assert_eq!(chunk, &t[..chunk.len()]);
2938                 t = &t[chunk.len()..];
2939                 last_chunk = chunk;
2940             }
2941 
2942             let c1 = {
2943                 let i2 = byte_to_char_idx(TEXT_LINES, i);
2944                 TEXT_LINES.chars().nth(i2).unwrap()
2945             };
2946             let c2 = {
2947                 let i2 = i - b;
2948                 let i3 = byte_to_char_idx(chunk, i2);
2949                 chunk.chars().nth(i3).unwrap()
2950             };
2951             assert_eq!(c1, c2);
2952         }
2953         assert_eq!(t.len(), 0);
2954     }
2955 
2956     #[test]
chunk_at_char()2957     fn chunk_at_char() {
2958         let r = Rope::from_str(TEXT_LINES);
2959         let mut t = TEXT_LINES;
2960 
2961         let mut last_chunk = "";
2962         for i in 0..r.len_chars() {
2963             let (chunk, b, c, l) = r.chunk_at_char(i);
2964             assert_eq!(b, char_to_byte_idx(TEXT_LINES, c));
2965             assert_eq!(l, char_to_line_idx(TEXT_LINES, c));
2966             if chunk != last_chunk {
2967                 assert_eq!(chunk, &t[..chunk.len()]);
2968                 t = &t[chunk.len()..];
2969                 last_chunk = chunk;
2970             }
2971 
2972             let c1 = TEXT_LINES.chars().nth(i).unwrap();
2973             let c2 = {
2974                 let i2 = i - c;
2975                 chunk.chars().nth(i2).unwrap()
2976             };
2977             assert_eq!(c1, c2);
2978         }
2979         assert_eq!(t.len(), 0);
2980     }
2981 
2982     #[test]
chunk_at_line_break()2983     fn chunk_at_line_break() {
2984         let r = Rope::from_str(TEXT_LINES);
2985 
2986         // First chunk
2987         {
2988             let (chunk, b, c, l) = r.chunk_at_line_break(0);
2989             assert_eq!(chunk, &TEXT_LINES[..chunk.len()]);
2990             assert_eq!(b, 0);
2991             assert_eq!(c, 0);
2992             assert_eq!(l, 0);
2993         }
2994 
2995         // Middle chunks
2996         for i in 1..r.len_lines() {
2997             let (chunk, b, c, l) = r.chunk_at_line_break(i);
2998             assert_eq!(chunk, &TEXT_LINES[b..(b + chunk.len())]);
2999             assert_eq!(c, byte_to_char_idx(TEXT_LINES, b));
3000             assert_eq!(l, byte_to_line_idx(TEXT_LINES, b));
3001             assert!(l < i);
3002             assert!(i <= byte_to_line_idx(TEXT_LINES, b + chunk.len()));
3003         }
3004 
3005         // Last chunk
3006         {
3007             let (chunk, b, c, l) = r.chunk_at_line_break(r.len_lines());
3008             assert_eq!(chunk, &TEXT_LINES[(TEXT_LINES.len() - chunk.len())..]);
3009             assert_eq!(chunk, &TEXT_LINES[b..]);
3010             assert_eq!(c, byte_to_char_idx(TEXT_LINES, b));
3011             assert_eq!(l, byte_to_line_idx(TEXT_LINES, b));
3012         }
3013     }
3014 
3015     #[test]
slice_01()3016     fn slice_01() {
3017         let r = Rope::from_str(TEXT);
3018 
3019         let s = r.slice(0..r.len_chars());
3020 
3021         assert_eq!(TEXT, s);
3022     }
3023 
3024     #[test]
slice_02()3025     fn slice_02() {
3026         let r = Rope::from_str(TEXT);
3027 
3028         let s = r.slice(5..21);
3029 
3030         assert_eq!(&TEXT[5..21], s);
3031     }
3032 
3033     #[test]
slice_03()3034     fn slice_03() {
3035         let r = Rope::from_str(TEXT);
3036 
3037         let s = r.slice(31..97);
3038 
3039         assert_eq!(&TEXT[31..109], s);
3040     }
3041 
3042     #[test]
slice_04()3043     fn slice_04() {
3044         let r = Rope::from_str(TEXT);
3045 
3046         let s = r.slice(53..53);
3047 
3048         assert_eq!("", s);
3049     }
3050 
3051     #[test]
3052     #[should_panic]
slice_05()3053     fn slice_05() {
3054         let r = Rope::from_str(TEXT);
3055         r.slice(53..52);
3056     }
3057 
3058     #[test]
3059     #[should_panic]
slice_06()3060     fn slice_06() {
3061         let r = Rope::from_str(TEXT);
3062         r.slice(102..104);
3063     }
3064 
3065     #[test]
eq_rope_01()3066     fn eq_rope_01() {
3067         let r = Rope::from_str("");
3068 
3069         assert_eq!(r, r);
3070     }
3071 
3072     #[test]
eq_rope_02()3073     fn eq_rope_02() {
3074         let r = Rope::from_str(TEXT);
3075 
3076         assert_eq!(r, r);
3077     }
3078 
3079     #[test]
eq_rope_03()3080     fn eq_rope_03() {
3081         let r1 = Rope::from_str(TEXT);
3082         let mut r2 = r1.clone();
3083         r2.remove(26..27);
3084         r2.insert(26, "z");
3085 
3086         assert_ne!(r1, r2);
3087     }
3088 
3089     #[test]
eq_rope_04()3090     fn eq_rope_04() {
3091         let r = Rope::from_str("");
3092 
3093         assert_eq!(r, "");
3094         assert_eq!("", r);
3095     }
3096 
3097     #[test]
eq_rope_05()3098     fn eq_rope_05() {
3099         let r = Rope::from_str(TEXT);
3100 
3101         assert_eq!(r, TEXT);
3102         assert_eq!(TEXT, r);
3103     }
3104 
3105     #[test]
eq_rope_06()3106     fn eq_rope_06() {
3107         let mut r = Rope::from_str(TEXT);
3108         r.remove(26..27);
3109         r.insert(26, "z");
3110 
3111         assert_ne!(r, TEXT);
3112         assert_ne!(TEXT, r);
3113     }
3114 
3115     #[test]
eq_rope_07()3116     fn eq_rope_07() {
3117         let r = Rope::from_str(TEXT);
3118         let s: String = TEXT.into();
3119 
3120         assert_eq!(r, s);
3121         assert_eq!(s, r);
3122     }
3123 
3124     #[test]
to_string_01()3125     fn to_string_01() {
3126         let r = Rope::from_str(TEXT);
3127         let s: String = (&r).into();
3128 
3129         assert_eq!(r, s);
3130     }
3131 
3132     #[test]
to_cow_01()3133     fn to_cow_01() {
3134         use std::borrow::Cow;
3135         let r = Rope::from_str(TEXT);
3136         let cow: Cow<str> = (&r).into();
3137 
3138         assert_eq!(r, cow);
3139     }
3140 
3141     #[test]
to_cow_02()3142     fn to_cow_02() {
3143         use std::borrow::Cow;
3144         let r = Rope::from_str(TEXT);
3145         let cow: Cow<str> = (r.clone()).into();
3146 
3147         assert_eq!(r, cow);
3148     }
3149 
3150     #[test]
to_cow_03()3151     fn to_cow_03() {
3152         use std::borrow::Cow;
3153         let r = Rope::from_str("a");
3154         let cow: Cow<str> = (&r).into();
3155 
3156         // Make sure it's borrowed.
3157         if let Cow::Owned(_) = cow {
3158             panic!("Small Cow conversions should result in a borrow.");
3159         }
3160 
3161         assert_eq!(r, cow);
3162     }
3163 
3164     #[test]
from_rope_slice_01()3165     fn from_rope_slice_01() {
3166         let r1 = Rope::from_str(TEXT);
3167         let s = r1.slice(..);
3168         let r2: Rope = s.into();
3169 
3170         assert_eq!(r1, r2);
3171         assert_eq!(s, r2);
3172     }
3173 
3174     #[test]
from_rope_slice_02()3175     fn from_rope_slice_02() {
3176         let r1 = Rope::from_str(TEXT);
3177         let s = r1.slice(0..24);
3178         let r2: Rope = s.into();
3179 
3180         assert_eq!(s, r2);
3181     }
3182 
3183     #[test]
from_rope_slice_03()3184     fn from_rope_slice_03() {
3185         let r1 = Rope::from_str(TEXT);
3186         let s = r1.slice(13..89);
3187         let r2: Rope = s.into();
3188 
3189         assert_eq!(s, r2);
3190     }
3191 
3192     #[test]
from_rope_slice_04()3193     fn from_rope_slice_04() {
3194         let r1 = Rope::from_str(TEXT);
3195         let s = r1.slice(13..41);
3196         let r2: Rope = s.into();
3197 
3198         assert_eq!(s, r2);
3199     }
3200 
3201     #[test]
from_iter_01()3202     fn from_iter_01() {
3203         let r1 = Rope::from_str(TEXT);
3204         let r2: Rope = Rope::from_iter(r1.chunks());
3205 
3206         assert_eq!(r1, r2);
3207     }
3208 
3209     // Iterator tests are in the iter module
3210 }
3211