gpt4 book ai didi

rust - 线程 '
' 在 Rust 中溢出了它的堆栈

转载 作者:行者123 更新时间:2023-11-29 07:50:43 26 4
gpt4 key购买 nike

我在尝试这段代码时出错,它实现了一个简单的链表。

use std::rc::Rc;
use std::cell::RefCell;

struct Node {
a : Option<Rc<RefCell<Node>>>,
value: i32
}

impl Node {
fn new(value: i32) -> Rc<RefCell<Node>> {
let node = Node {
a: None,
value: value
};
Rc::new(RefCell::new(node))
}
}

fn main() {
let first = Node::new(0);
let mut t = first.clone();
for i in 1 .. 10_000
{
if t.borrow().a.is_none() {
t.borrow_mut().a = Some(Node::new(i));
}
if t.borrow().a.is_some() {
t = t.borrow().a.as_ref().unwrap().clone();
}
}
println!("Done!");
}

为什么会这样?这是否意味着 Rust 不如定位的安全?

更新:如果我添加这个方法,程序就不会崩溃。

impl Drop for Node {
fn drop(&mut self) {
let mut children = mem::replace(&mut self.a, None);

loop {
children = match children {
Some(mut n) => mem::replace(&mut n.borrow_mut().a, None),
None => break,
}
}
}
}

但我不确定这是不是正确的解决方案。

最佳答案

Does this mean that Rust is not as safe as positioned?

Rust 只对某些类型的故障是安全的;特别是内存损坏崩溃,记录在此处:http://doc.rust-lang.org/reference.html#behavior-considered-undefined

不幸的是,有时人们倾向于认为 Rust 能够更稳健地应对某些非内存损坏的故障。具体来说,你应该阅读 http://doc.rust-lang.org/reference.html#behavior-considered-undefined .

tldr;在 Rust 中,很多事情都会引起 panic 。 panic 将导致当前线程停止,执行关闭操作。

从表面上看,这可能类似于其他语言的内存损坏崩溃,但重要的是要理解,虽然它是应用程序故障,但它不是内存损坏故障。

例如,您可以通过在不同的线程中运行操作并在线程 panic (无论出于何种原因)时优雅地处理失败来处理类似异常的 panic 。

在这个具体示例中,您在堆栈上用尽了太多内存。

这个简单的例子也会失败:

fn main() {
let foo:&mut [i8] = &mut [1i8; 1024 * 1024];
}

(在大多数 rustc 上;取决于特定实现的堆栈大小)

我原以为使用 Box::new() 将你的分配移动到堆栈会在这个例子中修复它......

use std::rc::Rc;
use std::cell::RefCell;

#[derive(Debug)]
struct Node {
a : Option<Box<Rc<RefCell<Node>>>>,
value: i32
}

impl Node {
fn new(value: i32) -> Box<Rc<RefCell<Node>>> {
let node = Node {
a: None,
value: value
};
Box::new(Rc::new(RefCell::new(node)))
}
}

fn main() {
let first = Node::new(0);
let mut t = first.clone();
for i in 1 .. 10000
{
if t.borrow().a.is_none() {
t.borrow_mut().a = Some(Node::new(i));
}
if t.borrow().a.is_some() {
let c:Box<Rc<RefCell<Node>>>;
{ c = t.borrow().a.as_ref().unwrap().clone(); }
t = c;
println!("{:?}", t);
}
}
println!("Done!");
}

...但事实并非如此。我真的不明白为什么,但希望其他人可以查看此内容并发布更权威的答案,说明究竟是什么导致您的代码中的堆栈耗尽。

关于rust - 线程 '<main>' 在 Rust 中溢出了它的堆栈,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28914042/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com