[英]What does the rust compiler “error: can't capture dynamic environment in a fn item; use the || { … } closure form instead” mean, and how to fix it?
我得到一个生锈编译错误:
src/main.rs:33:31: 33:35 error: can't capture dynamic environment in a fn item; use the || { ... } closure form instead
发生错误是因为我有一个函数,我使用let
声明一个变量,然后有一个内部函数,我尝试使用这个被关闭的变量。
我相当肯定这是一个初学者的问题,所以如果这有一个非常直接的答案,请提前抱歉!
请注意,我正在使用此内部函数作为回调,因此使用闭包,就像
let closure_fn = | args | -> () { do stuff };
......对我来说不是一个合适的解决方案。
extern crate nickel;
use std::io::net::ip::Ipv4Addr;
use nickel::{ Nickel, Request, Response };
fn stub_3rd_party_function() -> String {
"hello world".to_string()
}
fn main() {
let mut server = Nickel::new();
// assume that the variable **must** be instantiated like this
let hello_text : String = stub_3rd_party_function();
fn hello_handler (_request: &Request, response: &mut Response) -> () {
response.send(hello_text.as_slice());
}
server.get("/hello", hello_handler);
server.listen(Ipv4Addr(0,0,0,0), 6767);
}
导致以下错误:
src/test.rs:12:23: 12:33 error: can't capture dynamic environment in a fn item; use the || { ... } closure form instead
src/test.rs:12 response.send(hello_text);
^~~~~~~~~~
src/test.rs:12:23: 12:33 error: unresolved name `hello_text`.
src/test.rs:12 response.send(hello_text);
^~~~~~~~~~
error: aborting due to 2 previous errors
现在,我从标准函数切换到闭包函数:
extern crate nickel;
use std::io::net::ip::Ipv4Addr;
use nickel::{ Nickel, Request, Response };
fn stub_3rd_party_function() -> String {
"hello world".to_string()
}
fn main() {
let mut server = Nickel::new();
// assume that the variable **must** be instantiated like this
let hello_text : String = stub_3rd_party_function();
let hello_handler = |_request: &Request, response: &mut Response| -> () {
response.send(hello_text.as_slice());
};
server.get("/hello", hello_handler);
server.listen(Ipv4Addr(0,0,0,0), 6767);
}
导致不同的错误:
src/test.rs:21:30: 21:43 error: mismatched types: expected `fn(&nickel::request::Request<'_>, &mut nickel::response::Response<'_,'_>)` but found `|&nickel::request::Request<'_>, &mut nickel::response::Response<'_,'_>|` (expected extern fn but found fn)
src/test.rs:21 server.get("/hello", hello_handler);
^~~~~~~~~~~~~
error: aborting due to previous error
是否有一种方法可以用正常的方式“封闭”封闭的功能?
由于我使用的库需要一个标准函数而不是一个闭包,我不能使用闭包。 但是如果我不使用闭包,我就无法关闭外部函数fn main () { ... }
中定义的变量,从而陷入困境。
注意上面,我使用字符串hello_text
来提供简洁的代码示例。 在这种情况下,使用静态变量就足够了。 但是,静态变量不会为我修复它,因为我需要能够在fn main()
中为函数调用的结果分配一个变量,然后在我的内部处理函数中使用它。
它说,因为它是一个简单的事实:一个函数无法捕获变量; 如果你把一个函数放在另一个函数中,那么函数在函数内部而不是在函数内部纯粹是命名空间的问题,并且使它绝对是私有的,并且对其他任何东西都是不可访问的。 如果需要这样的变量捕获,则必须使用闭包。
在您的具体情况下,功能是唯一的方法。 你应该考虑你的代码(我会这样写,以减少缩进,如果没有别的):
fn hello_handler(_request: &Request, response: &mut Response) {
response.send(hello_text);
}
fn main() {
let mut server = Nickel::new();
let hello_text = "hello world";
server.get("/hello", hello_handler);
server.listen(Ipv4Addr(0, 0, 0, 0), 6767);
}
正如您可以通过这种表达方式看到的那样, hello_text
显然无法从hello_handler
访问。 有必要如此的技术原因,每个请求都在自己的任务中处理。 在这种特殊情况下,静态是解决方案:
static HELLO_TEXT: &'static str = "hello world";
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.