aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGokul Soumya2022-12-24 11:21:38 +0000
committerBlaž Hrastnik2023-01-18 05:19:32 +0000
commitb2837ff3bea286ce7ccfba9b6fbcd861977caf83 (patch)
tree2dad402d6dcd21b4c1592c41aa079f4b02dc2c05
parent7a76c6cbbaf851d63cb4ca4be07c5d4c67afbbb2 (diff)
Minimize allocation when converting table rows to string
-rw-r--r--helix-term/src/ui/picker.rs6
-rw-r--r--helix-tui/src/text.rs21
-rw-r--r--helix-tui/src/widgets/table.rs7
3 files changed, 24 insertions, 10 deletions
diff --git a/helix-term/src/ui/picker.rs b/helix-term/src/ui/picker.rs
index e00fe1f8..05738ccf 100644
--- a/helix-term/src/ui/picker.rs
+++ b/helix-term/src/ui/picker.rs
@@ -733,7 +733,11 @@ impl<T: Item + 'static> Component for Picker<T> {
.map(|mut row| {
const TEMP_CELL_SEP: &str = " ";
- let line = row.cell_text().join(TEMP_CELL_SEP);
+ let line = row.cell_text().fold(String::new(), |mut s, frag| {
+ s.push_str(&frag);
+ s.push_str(TEMP_CELL_SEP);
+ s
+ });
// Items are filtered by using the text returned by menu::Item::filter_text
// but we do highlighting here using the text in Row and therefore there
diff --git a/helix-tui/src/text.rs b/helix-tui/src/text.rs
index 6970634b..a3e242fe 100644
--- a/helix-tui/src/text.rs
+++ b/helix-tui/src/text.rs
@@ -438,17 +438,30 @@ impl<'a> From<Vec<Spans<'a>>> for Text<'a> {
impl<'a> From<Text<'a>> for String {
fn from(text: Text<'a>) -> String {
- let lines: Vec<String> = text.lines.iter().map(String::from).collect();
- lines.join("\n")
+ String::from(&text)
}
}
impl<'a> From<&Text<'a>> for String {
fn from(text: &Text<'a>) -> String {
- let lines: Vec<String> = text.lines.iter().map(String::from).collect();
- lines.join("\n")
+ let size = text
+ .lines
+ .iter()
+ .flat_map(|spans| spans.0.iter().map(|span| span.content.len()))
+ .sum::<usize>()
+ + text.lines.len().saturating_sub(1); // for newline after each line
+ let mut output = String::with_capacity(size);
+
+ for spans in &text.lines {
+ for span in &spans.0 {
+ output.push_str(&span.content);
+ }
+ output.push('\n');
+ }
+ output
}
}
+
impl<'a> IntoIterator for Text<'a> {
type Item = Spans<'a>;
type IntoIter = std::vec::IntoIter<Self::Item>;
diff --git a/helix-tui/src/widgets/table.rs b/helix-tui/src/widgets/table.rs
index 539f6a61..2983072d 100644
--- a/helix-tui/src/widgets/table.rs
+++ b/helix-tui/src/widgets/table.rs
@@ -122,11 +122,8 @@ impl<'a> Row<'a> {
}
/// Returns the contents of cells as plain text, without styles and colors.
- pub fn cell_text(&self) -> Vec<String> {
- self.cells
- .iter()
- .map(|cell| String::from(&cell.content))
- .collect()
+ pub fn cell_text(&self) -> impl Iterator<Item = String> + '_ {
+ self.cells.iter().map(|cell| String::from(&cell.content))
}
}