1use super::{CharSeq, ParserResult, Parser, Succ, Fail, Error};
2
3pub struct Split<'a, T:'a> {
4 parser: &'a (Parser<T>+'a),
5 delim: &'a (Parser<String>+'a),
6 allow_trailing_delim: bool
7}
8
9pub fn split<'a, T>(p: &'a (Parser<T> + 'a), d: &'a (Parser<String> + 'a), a: bool) -> Split<'a, T> {
10 return Split{parser: p, delim: d, allow_trailing_delim: a};
11}
12
13impl<'a, T> Parser<Vec<T>> for Split<'a, T> {
14 #[allow(unused_variables)]
15 fn _parse(&self, cs: &mut CharSeq) -> ParserResult<Vec<T>> {
16 let mut succ = true;
17 let mut r = Vec::new();
18 match self.parser.parse(cs) {
19 Succ(c) => r.push(c),
20 Fail(m, l) => return Succ(r),
21 Error(m, l) => return Error(m, l)
22 }
23 while succ {
24 match self.delim.parse(cs) {
25 Succ(c) => (),
26 Fail(m, l) => break,
27 Error(m, l) => return Error(m, l)
28 }
29 match self.parser.parse(cs) {
30 Succ(c) => r.push(c),
31 Fail(m, l) => {
32 if self.allow_trailing_delim {
33 succ = false
34 } else {
35 return Fail(m, l)
36 }
37 },
38 Error(m, l) => return Error(m, l)
39 }
40 }
41 return Succ(r);
42 }
43}
44
45
46#[cfg(test)]
47#[allow(unused_variables)]
48#[allow(unused_imports)]
49mod tests {
50 use super::split;
51 use super::super::{CharSeq, re, ParserResult, Parser, Succ, Fail, Error};
52
53 #[test]
54 fn test_split1() {
55 let mut cs = CharSeq::new("a,b,c", "");
56 let s = re("[a-z]");
57 let c = ",";
58 let sp = split(&s, &c, false);
59 match cs.accept(&sp) {
60 Succ(r) => assert_eq!(r, vec!["a".to_string(), "b".to_string(), "c".to_string()]),
61 Fail(m, l) => assert!(false),
62 Error(m, l) => assert!(false),
63 }
64 }
65
66 #[test]
67 fn test_split2() {
68 let mut cs = CharSeq::new("a,b,c,", "");
69 let s = re("[a-z]");
70 let c = ",";
71 let sp = split(&s, &c, false);
72 match cs.accept(&sp) {
73 Fail(m, l) => (),
74 Succ(r) => assert!(false),
75 Error(m, l) => assert!(false),
76 }
77 }
78
79 #[test]
80 fn test_split3() {
81 let mut cs = CharSeq::new("a,b,c,", "");
82 let s = re("[a-z]");
83 let c = ",";
84 let sp = split(&s, &c, true);
85 match cs.accept(&sp) {
86 Succ(r) => assert_eq!(r, vec!["a".to_string(), "b".to_string(), "c".to_string()]),
87 Fail(m, l) => assert!(false),
88 Error(m, l) => assert!(false),
89 }
90 }
91
92 #[test]
93 fn test_split4() {
94 let mut cs = CharSeq::new("", "");
95 let s = re("[a-z]");
96 let c = ",";
97 let sp = split(&s, &c, false);
98 match cs.accept(&sp) {
99 Succ(r) => assert_eq!(0, r.len()),
100 Fail(m, l) => assert!(false, m),
101 Error(m, l) => assert!(false, m),
102 }
103 }
104
105}