成功時 (および失敗時) に serde_json::Value を返す関数を作成しています。以前の Rust では、以下のコード例のように、関数からデータを返すためにセミコロンを省略していました。
use serde_json::{Result, Value};
use core::result::Result as ResultCore;
fn returning_function() -> ResultCore<Value, Value> {
let data = r#"
{
"status": "ok",
"response": {
"data": "secret message!"
}
}
"#;
match str_to_json(data) {
Ok(json_data) => match json_data["status"].as_str() {
Some(status_str) => {
if status_str == "ok" {
Ok(json_data["response"].clone())
}
}
None => eprintln!("\"status\" was not a string")
}
Err(error) => eprintln!("something went wrong! here's what: {}", error)
}
Err(serde_json::Value::Null)
}
fn str_to_json(json_data: &str) -> Result<Value> {
Ok(serde_json::from_str(json_data)?)
}
理解できない部分があります。これはコンパイルされません。expected type ()
Rust のコンパイラは、「型が一致しません」と教えてくれますfound type serde_json::value::Value
。これで、コンパイルできる解決策が見つかりました。それは次のとおりです。
use serde_json::{Result, Value};
use core::result::Result as ResultCore;
fn returning_function() -> ResultCore<Value, Value> {
let data = r#"
{
"status": "ok",
"response": {
"data": "secret message!"
}
}
"#;
match str_to_json(data) {
Ok(json_data) => match json_data["status"].as_str() {
Some(status_str) => {
if status_str == "ok" {
return Ok(json_data["response"].clone());
// ^ added return statement here
}
}
None => eprintln!("\"status\" was not a string")
}
Err(error) => eprintln!("something went wrong! here's what: {}", error)
}
Err(serde_json::Value::Null)
}
fn str_to_json(json_data: &str) -> Result<Value> {
Ok(serde_json::from_str(json_data)?)
}
ステートメントを追加するreturn
と、コンパイラーは突然満足し、コンパイラーはそれについて何も言うことがなくなります。どうしてこれなの?セミコロンを省略しても return ステートメントを使用しても同じ意味を持つという印象を受けました — なぜここで違うのでしょうか?