Crate prse

source ·
Expand description

githubcrates-iodocs-rs


This crate provides the parse! macro to easily parse strings using a format args like syntax.

Prse is a no-std compatible small string parsing library with an emphasis on speed and ease of use.

The parse! and try_parse! macros can parse anything in the standard library that implements FromStr, or any type that implements Parse. (Which can be derived with the Parse macro)

§Examples

let input = "Person 5: Hello Bob!";
let name: &str;

// Calls try_parse and unwraps the result.
let five: u32 = parse!(input, "Person {}: Hello {name}!");
// We can also specify the return position
assert_eq!((name, five), parse!(input, "Person {1}: Hello {0}!"));

assert_eq!(five, 5);
assert_eq!(name, "Bob");
let input = "I hate apples!\nI love apricots!";

for fruit in input.lines().map(|l| try_parse!(l, "I love {}!")) {
    match fruit {
        Ok::<&str, _>(fruit) => assert_eq!(fruit, "apricots"),
        Err(e) => println!("{e:?}")
    }
}

Additionally you can use the Parse derive macro to help you parse custom types. For even more flexibility you can implement the Parse trait yourself for fully custom parsing such as hexadecimal number parsing.

use prse::{parse, Parse};

#[derive(Parse, PartialEq, Eq, Debug)]
#[prse = "({x}, {y})"]
struct Position {
    x: i32,
    y: i32,
}

let input = "(1, 3) + (-2, 9)";

let (lhs, rhs): (Position, Position) = parse!(input, "{} + {}");

assert_eq!(lhs, Position {x: 1, y: 3});
assert_eq!(rhs, Position {x: -2, y: 9});

§Repetition

You can parse multiple parts of a string using one of the following methods:

§Array

You can parse a string into an array of parsed elements using the following syntax {<var>:<sep>:<count>}.

let input = "My farm contains exactly 3 animals: Beatrice, Betsy, Callum";

// var = nothing, sep = ", " and count = 3
let array: [&str; 3] = parse!(input, "My farm contains exactly 3 animals: {:, :3}");

assert_eq!(array, ["Beatrice", "Betsy", "Callum"]);

§Vec

You can parse a string into a Vec of parsed elements using the following syntax {<var>:<sep>:}. This way of parsing is only available if the alloc feature has been enabled.

let input = "My farm contains some amount of booleans: true || false || true || false";
let many: Vec<bool>;

// var = many and sep = " || "
parse!(input, "My farm contains some amount of booleans: {many: || :}");

assert_eq!(many, vec![true, false, true, false]);

§Iterator

Alternatively if you are unable to allocate anything then you can use a lazy iterator by using the following syntax {<var>:<sep>:0}.

One important note is that since the iterator is evaluated lazily it will always return an iterator of Results.

The returned iterator will either be ParseIter or ParseChars if the separator is empty.

let input = "My farm has this many animals: [5,23,42,1,3,5]";

// var = nothing and sep = ","
let animal_count: u32 = parse!(input, "My farm has this many animals: [{:,:0}]")
    .flat_map(|c: Result<u32, _>| c.ok())
    .sum();

assert_eq!(animal_count, 79);

§Modifiers

All three multi-parsers (Array, Vec and Iterator) allow {<var>:<sep>:!<kind>} syntax to skip multiple separators, for example

assert_eq!([1, 2, 3], parse!("1-2---3", "{:-:!3}"));

§Empty separators

If the separator is an empty string slice (e.g. {::}) then the multi-parsers will iterate over every char in the string.

assert_eq!([3, 2, 1], parse!("321", "{::3}"))

Macros§

Structs§

  • An iterator that takes a string and parses all chars individually.
  • An iterator that takes a string and parses all items between each separator.

Enums§

Traits§

  • An str extension trait to allow you to call the from_str from Parse without specifying the type.
  • Parse a string into the implemented type, unlike FromStr this trait allows you to borrow the string. It can be automatically derived using Parse.

Derive Macros§

  • Automatically implements the Parse trait using one of two methods.