CodeBlanks Logo Icon CodeBlanks

Option and default

Learn Option fields and default values.

Option and default

In real data some fields may be missing. Option<T> fields become None if missing; #[serde(default)] puts the type's default into a missing field. When writing, skip_serializing_if is used to skip None fields:

#[derive(Serialize, Deserialize)]
struct Profil {
    ad: String,
    #[serde(skip_serializing_if = "Option::is_none")]
    sehir: Option<String>,
    #[serde(default)]
    puan: u32,               // 0 if missing from the JSON
}

Skipping by hand

To build the same behaviour by hand, we collect the fields in a list and add only the filled ones:

fn json(&self) -> String {
    let mut alanlar = vec![format!("\"ad\":\"{}\"", self.ad)];
    if let Some(s) = &self.sehir {
        alanlar.push(format!("\"sehir\":\"{}\"", s));
    }
    format!("{{{}}}", alanlar.join(","))
}

format!("{{{}}}", ..): the outer {{ and }} are literal braces, the middle {} is a placeholder.

Practice Optional city

Write the json method above for Profil { ad: String, sehir: Option<String> }, skipping a None city. Print the profiles Ece (no city) and Can (İzmir) on separate lines.

Starter code

main.rs
fn main() {
    // buraya yaz
}

Sample solution

main.rs
struct Profil {
    ad: String,
    sehir: Option<String>,
}

impl Profil {
    fn json(&self) -> String {
        let mut alanlar = vec![format!("\"ad\":\"{}\"", self.ad)];
        if let Some(s) = &self.sehir {
            alanlar.push(format!("\"sehir\":\"{}\"", s));
        }
        format!("{{{}}}", alanlar.join(","))
    }
}

fn main() {
    let a = Profil { ad: "Ece".into(), sehir: None };
    let b = Profil { ad: "Can".into(), sehir: Some("İzmir".into()) };
    println!("{}", a.json());
    println!("{}", b.json());
}

Expected output

{"ad":"Ece"}
{"ad":"Can","sehir":"İzmir"}

Questions and answers

Review the lesson questions together with their answers. To test yourself, solve the lesson interactively.

1 Without <code>skip_serializing_if</code>, how is <code>sehir: None</code> written?

  • It errors
  • "sehir":null Correct answer
  • It isn't written at all
  • "sehir":""

Explanation: serde turns None into JSON null; skipping the field entirely needs skip_serializing_if.

2 Default value

Question
#[serde(____)]
puan: u32,   // JSON'da yoksa 0
Answer
#[serde(default)]
puan: u32,   // JSON'da yoksa 0

Explanation: #[serde(default)] puts Default::default() into a missing field.

3 Attribute and effect

Term Meaning
Option<T> None if missing
#[serde(default)] Default if missing
skip_serializing_if Skip by condition
#[serde(skip)] Never write/read

All lessons in Intermediate