I'm trying to implement a simple string parser by iterating over each character. To keep track of line and column number, I'm storing the iterator inside a struct. Here's my attempt:
struct ParseState<'a> {
iter: &'a mut Chars<'a>
, peeked_char: Option<char>
, num_line: u32
, num_char: u32
}
impl ParseState<'_> {
fn new(s: &String) -> ParseState {
ParseState { iter: &mut s.chars()
, peeked_char: None
, num_line: 0
, num_char: 0
}
}
fn peek(&mut self) -> Option<char> {
if !self.peeked_char.is_some() {
self.peeked_char = self.next();
}
self.peeked_char
}
}
impl Iterator for ParseState<'_> {
type Item = char;
fn next(&mut self) -> Option<Self::Item> {
if self.peeked_char.is_some() {
let c = self.peeked_char;
self.peeked_char = None;
return c
}
let c = self.iter.next();
if c.is_some() {
self.num_char += 1;
if c.unwrap() == '\n' {
self.num_line += 1;
self.num_char = 0;
}
}
c
}
}
But it fails to compile:
warning: unused variable: `m`
--> src/lib.rs:15:7
|
15 | let m = input_parsers::parse_satlib(&s);
| ^ help: if this is intentional, prefix it with an underscore: `_m`
|
= note: `#[warn(unused_variables)]` on by default
error[E0515]: cannot return value referencing temporary value
--> src/input_parsers.rs:17:5
|
17 | ParseState { iter: &mut s.chars()
| ^ --------- temporary value created here
| _____|
| |
18 | | , peeked_char: None
19 | | , num_line: 0
20 | | , num_char: 0
21 | | }
| |________________^ returns a value referencing data owned by the current function
|
= help: use `.collect()` to allocate the iterator
For more information about this error, try `rustc --explain E0515`.
warning: `erisat` (lib) generated 1 warning
error: could not compile `erisat` due to previous error; 1 warning emitted
I know it has to do with borrowed ownership, but I'm a complete Rust newbie so I'm unable to know what to do to work around this.