ข้ามไปยังเนื้อหา

ประเภท Result

Result<T, E> คือประเภทมาตรฐานของ Rust สำหรับการดำเนินการที่สามารถสำเร็จหรือล้มเหลวได้ในลักษณะที่คาดหวังได้ โดยกำหนดไว้ใน standard library ดังนี้:

enum Result<T, E> {
Ok(T),
Err(E),
}
  • Ok(T) — การดำเนินการสำเร็จและสร้างค่าประเภท T
  • Err(E) — การดำเนินการล้มเหลวและสร้างค่าข้อผิดพลาดประเภท E

ทั้ง T และ E เป็นพารามิเตอร์ generic ที่คุณกำหนด ตัวอย่างเช่น Result<i32, String> สำเร็จด้วย i32 หรือล้มเหลวด้วยข้อความ String

เพื่อส่งสัญญาณความล้มเหลวที่กู้คืนได้จากฟังก์ชัน ให้เปลี่ยนประเภทการคืนค่าเป็น Result<T, E> และคืน Ok(value) เมื่อสำเร็จ หรือ Err(error) เมื่อล้มเหลว:

fn parse_age(s: &str) -> Result<u32, String> {
s.parse::<u32>().map_err(|e| format!("parse error: {}", e))
}

การเรียก .map_err แปลงข้อผิดพลาดการแยกวิเคราะห์ของ standard library เป็นประเภท String ข้อผิดพลาดของคุณเอง

วิธีที่ชัดเจนที่สุดในการจัดการ Result คือนิพจน์ match — บังคับให้คุณจัดการทั้งสองสาขา:

fn parse_age(s: &str) -> Result<u32, String> {
s.parse::<u32>().map_err(|e| format!("parse error: {}", e))
}
fn main() {
match parse_age("25") {
Ok(age) => println!("Parsed age: {}", age),
Err(e) => println!("Error: {}", e),
}
}

สำหรับโค้ดที่กระชับกว่า Result มีเมธอดหลายตัว:

เมธอดพฤติกรรม
.unwrap()คืนค่า Ok; panic เมื่อ Err
.expect(msg)เหมือนกัน แต่มีข้อความ panic ที่กำหนดเอง
.unwrap_or(default)คืนค่า Ok หรือค่าเริ่มต้น
.unwrap_or_else(|e| ...)คืนค่า Ok หรือคำนวณค่าเริ่มต้นจากข้อผิดพลาด
.is_ok() / .is_err()การทดสอบ boolean โดยไม่ดึงค่า
.map(|v| ...)แปลงค่า Ok ไม่เปลี่ยน Err
.map_err(|e| ...)แปลงค่า Err ไม่เปลี่ยน Ok
fn parse_age(s: &str) -> Result<u32, String> {
s.parse::<u32>().map_err(|e| format!("parse error: {}", e))
}
fn main() {
// Match on Result to handle both branches
match parse_age("25") {
Ok(age) => println!("Parsed age: {}", age),
Err(e) => println!("Error: {}", e),
}
// .unwrap_or returns a default on Err
let age1 = parse_age("abc").unwrap_or(0);
println!("unwrap_or default: {}", age1);
// .unwrap_or_else lets you compute the default
let age2 = parse_age("not_a_number").unwrap_or_else(|e| {
println!("Recovering from: {}", e);
18
});
println!("unwrap_or_else result: {}", age2);
// is_ok / is_err for simple checks
println!("parse_age(\"30\") is_ok: {}", parse_age("30").is_ok());
println!("parse_age(\"xx\") is_err: {}", parse_age("xx").is_err());
}
สอง variant ของ Result<T, E> คืออะไร?
.unwrap_or_else(|e| ...) ทำอะไรเมื่อ Result เป็น Err(e)?
เมธอดใดที่แปลงค่า Ok โดยไม่แตะ Err?
เหตุใดคอมไพเลอร์ Rust จึงเตือนเมื่อ Result ไม่ได้ใช้?