首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >‘`for<'r,'r,'r> ...`不能安全地在线程之间发送

‘`for<'r,'r,'r> ...`不能安全地在线程之间发送
EN

Stack Overflow用户
提问于 2016-08-25 09:43:17
回答 1查看 2.7K关注 0票数 5

我学习了Rust,并试图构建一个建立在hyper之上的微路由系统(这只是为了学习目的,我知道框架是存在的)。

我不知道如何与hyper::server::Handler共享“复杂”类型。我阅读了错误消息,但不幸的是,我不知道如何修复它(大多数情况下,生锈编译器只是说要修复什么,现在我还不确定是否理解)。

下面是我尝试过的一个(非)工作过度简化的例子:

代码语言:javascript
复制
extern crate hyper;
use std::sync::Mutex;

use hyper::*;

type Route = (method::Method, String, Box<Fn(server::Request, server::Response)>);

struct MyHandler {
    routes: Mutex<Vec<Route>>
}

impl server::Handler for MyHandler {
    fn handle(&self, req: server::Request, mut res: server::Response) {
        // This is not important
    }
}

fn main() {
    // This is not important
}

错误是:

代码语言:javascript
复制
error: the trait bound `for<'r, 'r, 'r> std::ops::Fn(hyper::server::Request<'r, 'r>, hyper::server::Response<'r>) + 'static: std::marker::Send` is not satisfied [--explain E0277]
  --> src/main.rs:12:10
   |>
12 |>     impl server::Handler for MyHandler {
   |>          ^^^^^^^^^^^^^^^
note: `for<'r, 'r, 'r> std::ops::Fn(hyper::server::Request<'r, 'r>, hyper::server::Response<'r>) + 'static` cannot be sent between threads safely
note: required because it appears within the type `Box<for<'r, 'r, 'r> std::ops::Fn(hyper::server::Request<'r, 'r>, hyper::server::Response<'r>) + 'static>`
note: required because it appears within the type `(hyper::method::Method, std::string::String, Box<for<'r, 'r, 'r> std::ops::Fn(hyper::server::Request<'r, 'r>, hyper::server::Response<'r>) + 'static>)`
note: required because of the requirements on the impl of `std::marker::Send` for `std::ptr::Unique<(hyper::method::Method, std::string::String, Box<for<'r, 'r, 'r> std::ops::Fn(hyper::server::Request<'r, 'r>, hyper::server::Response<'r>) + 'static>)>`
note: required because it appears within the type `alloc::raw_vec::RawVec<(hyper::method::Method, std::string::String, Box<for<'r, 'r, 'r> std::ops::Fn(hyper::server::Request<'r, 'r>, hyper::server::Response<'r>) + 'static>)>`
note: required because it appears within the type `std::vec::Vec<(hyper::method::Method, std::string::String, Box<for<'r, 'r, 'r> std::ops::Fn(hyper::server::Request<'r, 'r>, hyper::server::Response<'r>) + 'static>)>`
note: required because of the requirements on the impl of `std::marker::Send` for `std::sync::Mutex<std::vec::Vec<(hyper::method::Method, std::string::String, Box<for<'r, 'r, 'r> std::ops::Fn(hyper::server::Request<'r, 'r>, hyper::server::Response<'r>) + 'static>)>>`
note: required because it appears within the type `MyHandler`
note: required by `hyper::server::Handler`

如果我使用一个简单的整数,但不使用Route类型,它就能工作。

因此,这种特性和“不能安全地在线程之间发送”的特性存在问题。阅读hyper文档后,我添加了一个Mutex,但我一定很笨,我不知道自己在做什么,不知道是该停下来学习Rust,还是继续尝试。

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2016-08-25 11:00:00

你就快到了。

错误是说MyHandler没有实现Send特性,这意味着可以安全地将类型发送到其他线程:

代码语言:javascript
复制
note: required because of the requirements on the impl of `std::marker::Send` for `std::sync::Mutex<std::vec::Vec<(hyper::method::Method, std::string::String, Box<for<'r, 'r, 'r> std::ops::Fn(hyper::server::Request<'r, 'r>, hyper::server::Response<'r>) + 'static>)>>`
note: required because it appears within the type `MyHandler`
note: required by `hyper::server::Handler`

这个错误确实指向了正确的地方,但它有点让人难以抗拒。第一行是:

代码语言:javascript
复制
note: `for<'r, 'r, 'r> std::ops::Fn(hyper::server::Request<'r, 'r>, hyper::server::Response<'r>) + 'static` cannot be sent between threads safely

也就是说,Fn类型不实现Send。这是您的Route类型中的一个:

代码语言:javascript
复制
type Route = (method::Method, String, Box<Fn(server::Request, server::Response)>);

如果Fn闭包捕获的所有变量也都是Send,则它的闭包仅为Send,但在这里我们不知道传入的任何闭包是否合适。

解决方案很简单:将Fn类型约束为Send

代码语言:javascript
复制
type Route = (method::Method, String, Box<Fn(server::Request, server::Response)+Send>);
票数 7
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/39141810

复制
相关文章

相似问题

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