Skip to content

Instantly share code, notes, and snippets.

@Lisoph
Created April 26, 2017 07:06
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save Lisoph/8524d5bc499af73ef36a960dfdb1d88e to your computer and use it in GitHub Desktop.
Save Lisoph/8524d5bc499af73ef36a960dfdb1d88e to your computer and use it in GitHub Desktop.
#![feature(conservative_impl_trait)]
fn take<'a>(take: &'a str) -> impl Fn(&'a str) -> (&'a str, &'a str) {
move |input| {
let len = input.chars().zip(take.chars()).take_while(|&(i, t)| i == t).count();
(&input[0..len], &input[len..])
}
}
fn chain<'a, F1, F2>(first: F1, second: F2) -> impl Fn(&'a str) -> ((&'a str, &'a str), &'a str)
where
F1: Fn(&'a str) -> (&'a str, &'a str),
F2: Fn(&'a str) -> (&'a str, &'a str)
{
move |input| {
let (res1, rem1) = first(input);
let (res2, rem2) = second(rem1);
((res1, res2), rem2)
}
}
fn map<'a, R, T, N, F>(parser: F, trans: T) -> impl Fn(&'a str) -> (N, &'a str)
where
T: Fn(R) -> N,
F: Fn(&'a str) -> (R, &'a str)
{
move |input| {
let (res, rem) = parser(input);
(trans(res), rem)
}
}
fn main() {
let parse_hello = chain(take("hel"), take("lo"));
let parse_hello_string = map(|i| parse_hello(i), |(lhs, rhs)| format!("{}{}", lhs, rhs));
println!("{:?}", parse_hello("hello world"));
println!("{:?}", parse_hello_string("hello world"));
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment