aboutsummaryrefslogtreecommitdiff
path: root/crates/stdx/src
diff options
context:
space:
mode:
Diffstat (limited to 'crates/stdx/src')
-rw-r--r--crates/stdx/src/lib.rs75
1 files changed, 75 insertions, 0 deletions
diff --git a/crates/stdx/src/lib.rs b/crates/stdx/src/lib.rs
new file mode 100644
index 000000000..a01ca6d4d
--- /dev/null
+++ b/crates/stdx/src/lib.rs
@@ -0,0 +1,75 @@
1//! Missing batteries for standard libraries.
2
3use std::{cell::Cell, fmt};
4
5/// Appends formatted string to a `String`.
6#[macro_export]
7macro_rules! format_to {
8 (&buf:expr) => ();
9 ($buf:expr, $lit:literal $($arg:tt)*) => {
10 { use ::std::fmt::Write as _; let _ = ::std::write!($buf, $lit $($arg)*); }
11 };
12}
13
14pub trait SepBy: Sized {
15 /// Returns an `impl fmt::Display`, which joins elements via a separator.
16 fn sep_by<'a>(self, sep: &'a str) -> SepByBuilder<'a, Self>;
17}
18
19impl<I> SepBy for I
20where
21 I: Iterator,
22 I::Item: fmt::Display,
23{
24 fn sep_by<'a>(self, sep: &'a std::primitive::str) -> SepByBuilder<'a, Self> {
25 SepByBuilder::new(sep, self)
26 }
27}
28
29pub struct SepByBuilder<'a, I> {
30 sep: &'a str,
31 prefix: &'a str,
32 suffix: &'a str,
33 iter: Cell<Option<I>>,
34}
35
36impl<'a, I> SepByBuilder<'a, I> {
37 fn new(sep: &'a str, iter: I) -> SepByBuilder<'a, I> {
38 SepByBuilder { sep, prefix: "", suffix: "", iter: Cell::new(Some(iter)) }
39 }
40
41 pub fn prefix(mut self, prefix: &'a str) -> Self {
42 self.prefix = prefix;
43 self
44 }
45
46 pub fn suffix(mut self, suffix: &'a str) -> Self {
47 self.suffix = suffix;
48 self
49 }
50
51 /// Set both suffix and prefix.
52 pub fn surround_with(self, prefix: &'a str, suffix: &'a str) -> Self {
53 self.prefix(prefix).suffix(suffix)
54 }
55}
56
57impl<I> fmt::Display for SepByBuilder<'_, I>
58where
59 I: Iterator,
60 I::Item: fmt::Display,
61{
62 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
63 f.write_str(self.prefix)?;
64 let mut first = true;
65 for item in self.iter.take().unwrap() {
66 if !first {
67 f.write_str(self.sep)?;
68 }
69 first = false;
70 fmt::Display::fmt(&item, f)?;
71 }
72 f.write_str(self.suffix)?;
73 Ok(())
74 }
75}