Я пытаюсь выполнить обработку ошибок при использовании .iter()
в сочетании с .flat_map
, в котором есть .iter().map()
.
Сценарий получает все Event
, которые принадлежат группе организаций, где вложенные .iter().map()
используются для получения участников каждого события, объединяют это с событием и возвращают EventResponse
stuct.
Неописанным способом описания проблемы может быть «Как получить Result<Vec<T>, err>
из вложенного flat_map Result<Vec<T>, err>
, который имеет вложенную карту Result<T, err>
»
Ниже приведена абстрагированная / упрощенная версия кода, который я использую, который дает мне те же ошибки, что и мой настоящий код.
struct Event {
id: usize,
}
#[derive(Debug)]
struct EventResponse {
id: usize,
participants: Vec<i32>,
}
fn main() {
let orgs = vec![1, 3, 14, 12];
let events: Result<Vec<EventResponse>, &str> = orgs
.iter()
.flat_map::<Result<Vec<EventResponse>, &str>, _>(|org_id| {
get_events_for(*org_id)
.map_err(|_| "That Org id does not exist")
.map(|events| {
events
.iter()
.map::<Result<EventResponse, &str>, _>(|event| {
get_event_with_participants(event)
.map(|event_response| event_response)
.map_err(|_| "Participants for that event were not found")
})
.collect()
})
})
.collect();
}
fn get_events_for(id: usize) -> Result<Vec<Event>, ()> {
// pretend we are checking against a database of existing org ids, if the org id does not exist, then return an error
if id == 3 {
Ok(vec![Event { id }])
} else {
Err(())
}
}
fn get_event_with_participants(event: &Event) -> Result<EventResponse, ()> {
//pretend the participants are fetched from a database
let foundParticipants = true;
if foundParticipants {
Ok(EventResponse {
id: event.id,
participants: vec![1, 2, 5],
})
} else {
Err(())
}
}
Playground
Типовые аннотации должны показывать, что ожидается на каждом этапе. Я ожидаю, что events
будет иметь тип Result<Vec<EventResponse>, &str>
, но я получаю 2 ошибки:
error[E0277]: a collection of type `std::vec::Vec<EventResponse>` cannot be built from an iterator over elements of type `std::result::Result<EventResponse, &str>`
--> example.rs:27:26
|
27 | .collect()
| ^^^^^^^ a collection of type `std::vec::Vec<EventResponse>` cannot be built from `std::iter::Iterator<Item=std::result::Result<EventResponse, &str>>`
|
= help: the trait `std::iter::FromIterator<std::result::Result<EventResponse, &str>>` is not implemented for `std::vec::Vec<EventResponse>`
error[E0277]: a collection of type `std::result::Result<std::vec::Vec<EventResponse>, &str>` cannot be built from an iterator over elements of type `std::vec::Vec<EventResponse>`
--> example.rs:30:10
|
30 | .collect();
| ^^^^^^^ a collection of type `std::result::Result<std::vec::Vec<EventResponse>, &str>` cannot be built from `std::iter::Iterator<Item=std::vec::Vec<EventResponse>>`
|
= help: the trait `std::iter::FromIterator<std::vec::Vec<EventResponse>>` is not implemented for `std::result::Result<std::vec::Vec<EventResponse>, &str>`
РЕДАКТИРОВАТЬ: get_events_for
функция не может быть изменена , однако, get_event_with_participants
функция может быть изменена , если это поможет.