我无法使用 serde 将 json 字符串反序列化为结构

Ale*_*aev 5 rust serde

我在将 json 反序列化为结构时遇到问题。

这是模拟我的问题的代码:

use std::sync::mpsc;
use std::sync::mpsc::{Receiver, Sender };

extern crate serde_json;
extern crate serde;
#[macro_use]
extern crate serde_derive;

#[derive(Deserialize, Debug)]
struct Foo<'a> {
    a: u32,
    b: u32,
    c: &'a str,
}

fn main() {

    let (msg_tx, msg_rx): (Sender<Foo>, Receiver<Foo>) = mpsc::channel();
    {
        let js = r#"{"a":33, "b":44, "c": "ss"}"#; // initially I have a json String, here I simulate a problem
        let js_string = String::from(js);
        let f = test(js_string.as_str());

        msg_tx.send(f);
    }
}

fn test(js: &str) -> Foo {
    let foo: Foo = serde_json::from_str(js).unwrap();

    foo
}

Run Code Online (Sandbox Code Playgroud)

运行该代码会导致错误'js' does not live long enough。我知道将 Foo c 字段的类型更改为 String 可以解决问题,但我想知道是否还有其他解决方案。这个错误的原因是 serde crate 在这种情况下的工作方式, - 它在返回的foo变量内部使用对原始变量的引用,即 js_string ,因此它在调用后就超出了范围,msg_tx.send(f);但 f 有对其的引用并且寿命更长比那个范围。我仍然是 Rust 初学者,想掌握终生概念。我尝试使用函数包装器来解决我的问题以设置正确的生命周期,但失败了。

Yan*_*unk 5

您必须确保其js_string寿命比通道长,为了确保这一点,您可以创建一个与通道“工作”的范围:

use std::sync::mpsc;
use std::sync::mpsc::{Receiver, Sender };

extern crate serde_json;
extern crate serde;
#[macro_use]
extern crate serde_derive;

#[derive(Deserialize, Debug)]
struct Foo<'a> {
    a: u32,
    b: u32,
    c: &'a str,
}

fn main() {

    let js = r#"{"a":33, "b":44, "c": "ss"}"#;
    let js_string = String::from(js);
    let f = test(js_string.as_str());
    {
        let (msg_tx, msg_rx): (Sender<Foo>, Receiver<Foo>) = mpsc::channel();
        msg_tx.send(f);
        
    } // channel is dropped here and js_string is no longer borrowed


} // js_string is dropped here

fn test(js: &str) -> Foo {
    let foo: Foo = serde_json::from_str(js).unwrap();
    foo
}
Run Code Online (Sandbox Code Playgroud)