簡體   English   中英

在 Rust 中隱藏並與借用檢查器作斗爭

[英]Shadowing in Rust and Fighting the Borrow Checker

每次我接受用戶輸入時,我都會創建一個新變量(通過陰影)來獲取輸入。 我認為這是低效的,而不是陰影的目的,我還能如何有效地重用變量輸入?

如果沒有陰影,它會導致錯誤cannot borrow "input" as mutable because it is also borrowed as immutable 據我了解,獲取用戶輸入需要一個可變引用。

use std::io; // Import for IO

fn main() {
    let name: &str;                 // Variables
    let balance: f32;               // Variables
    let interest: f32;              // Variables
    let mut input = String::new();  // Variables

    println!("Please enter your name: "); // Print
    io::stdin().read_line(&mut input).expect("failed to read from stdin");
    name = input.trim();
    println!("Please enter your bank account balance: "); // Print

    loop {
        let mut input = String::new(); // Remove this and I get an error
        io::stdin().read_line(&mut input).expect("failed to read from stdin");

        match input.trim().parse::<f32>() {
            Ok(_) => {
                balance = input.trim().parse().unwrap();
                break;
            },
            Err(_) => println!("Your balance cannot contain letters or symbols"),};
        }
    }

    println!("Please enter your interest rate percent: "); // Print
     
    loop {
        let mut input = String::new(); // Remove this and I get an error
        io::stdin().read_line(&mut input).expect("failed to read from stdin");
    
        match input.trim().parse::<f32>() {
            Ok(_) =>  {   
                interest = input.trim().parse().unwrap();
                break;
            },
            Err(_) => println!("Your balance cannot contain letters or symbols"),};       
        }
    }

    println!("{}, your gain from interest is : ${}", name, (interest * balance * 0.01)); // Print
}

來自 Java,我對借用的工作方式以及何時隱藏是一個好主意感到困惑。 我知道舊值仍然存在,並且任何對它的引用都意味着如果您不再需要舊值,那么您將無緣無故地占用資源。 任何建議都有幫助,謝謝。

該錯誤告訴您問題:

error[E0502]: cannot borrow `input` as mutable because it is also borrowed as immutable
  --> src/main.rs:20:27
   |
13 |     name = input.trim();
   |            ----- immutable borrow occurs here
...
20 |     io::stdin().read_line(&mut input).expect("failed to read from stdin");
   |                           ^^^^^^^^^^ mutable borrow occurs here
...
47 |     println!("{}, your gain from interest is : ${}", name, (interest * balance * 0.01)); //Print
   |                                                      ---- immutable borrow later used here

input.trim()創建一個對 input 的不可變引用並將其存儲在name 如果刪除String::new()調用,那么您正在調用io::stdin().read_line(&mut input) ,它接受對輸入的可變引用,但在name變量中仍然存在對輸入的不可變引用。

在 Rust 中,不允許不可變引用和可變引用同時存在,因此編譯器會報錯。

你不能真正在這里重用變量,你需要克隆或做你正在做的事情並完全創建一個新的字符串。

HexCoder 的回答解釋了您不能在input重用String ,因為它是由name借用的。 但是,為了使其可重用,您需要做的就是將input.trim()復制到一個帶有自己的緩沖區的新String

let name: String = input.trim().into();

由於name不再借用input ,您可以擦除input並重新使用其緩沖區。 要擦除字符串,請使用String::clear

input.clear(); // instead of `input = String::new();`

這是一個更完整的示例,其中我還使用模式綁定來避免對input兩次解析,並將balanceinterest的聲明移至可以立即初始化的位置。

也可以看看

變量陰影有一些微妙之處,尤其是當您考慮編譯器優化時; 這些問題也可能有用:

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM