首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >使用?内部闭包

使用?内部闭包
EN

Stack Overflow用户
提问于 2019-03-06 04:24:28
回答 1查看 95关注 0票数 1

我得到了这个简单的解析函数

代码语言:javascript
复制
use std::collections::BTreeMap;

fn parse_kv(data: &str) -> BTreeMap<String, String> {
    data.split('&')
        .map(|kv| kv.split('='))
        .map(|mut kv| (kv.next().unwrap().into(), kv.next().unwrap().into()))
        .collect()
}

#[test]
fn parse_kv_test() {
    let result = parse_kv("test1=1&test2=2");
    assert_eq!(result["test1"], "1");
    assert_eq!(result["test2"], "2");
}

它工作得很好,但我希望有如下的选项或结果返回类型:

代码语言:javascript
复制
fn parse_kv(data: &str) -> Option<BTreeMap<String, String>>

此实现:

代码语言:javascript
复制
fn parse_kv(data: &str) -> Option<BTreeMap<String, String>> {
    Some(data.split('&')
        .map(|kv| kv.split('='))
        .map(|mut kv| (kv.next()?.into(), kv.next()?.into()))
        .collect())
}

不幸的是,它给出了以下错误:

代码语言:javascript
复制
error[E0277]: the `?` operator can only be used in a function that returns `Result` or `Option` (or another type that implements `std::ops::Try`)
  --> src/ecb_cut_paste.rs:23:24
   |
23 |         .map(|mut kv| (kv.next()?.into(), kv.next()?.into()))
   |                        ^^^^^^^^^^ cannot use the `?` operator in a function that returns `(_, _)`
   |
   = help: the trait `std::ops::Try` is not implemented for `(_, _)`
   = note: required by `std::ops::Try::from_error`

有没有可能在闭包中使用?运算符从这样的函数返回None?如果不是,我需要如何处理这样的情况呢?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2019-03-06 05:19:32

这里的问题是闭包本身是一个函数,所以使用?将从闭包返回,而不是外部函数。但是,这仍然可以用来以您想要的方式实现函数:

代码语言:javascript
复制
use std::collections::BTreeMap;

fn parse_kv(data: &str) -> Option<BTreeMap<String, String>> {
    data.split('&')
        .map(|kv| kv.split('='))
        .map(|mut kv| Some((kv.next()?.into(), kv.next()?.into())))
        .collect()
}

#[test]
fn parse_kv_test() {
    let result = parse_kv("test1=1&test2=2").unwrap();
    assert_eq!(result["test1"], "1");
    assert_eq!(result["test2"], "2");

    let result2 = parse_kv("test1=1&test2");
    assert_eq!(result2, None);
}

这里有几点需要注意:首先,第二个map调用中的问号和Some(...)意味着您有一个Option<(String, String)>类型推理的迭代器为您解决这个问题。

下一点值得注意的是,collect()可以自动将Iterator<Option<T>>转换为Option<Collection<T>> (与Result -relevant documentation here相同)。我添加了一个测试,演示了它的工作原理。

另一件需要注意的事情是,以这种方式使用collect仍然允许短路。一旦迭代器产生第一个Nonecollect将立即返回None,而不是继续处理每个元素。

票数 5
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/55010980

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档