如何解决是否可以在Rust中执行对块表达式的捕获?
我要说的那种简单例子:
let x = 10;
if true {
let x = 20;
}
println!("x is {}",x);
这将打印x is 10
,而不是x is 20
,并给我一个未使用的变量警告,因为if块中的x
与它外面的x
不同。有没有一种方法可以对if执行类似捕获的操作,从而使其实际作用于包含块的x
?
我在这里想象通过重复的let
语句执行阴影处理是可取的,但是如果它只是一个int
,则示例更加简洁。用伪代码,也许会更像是:
let data = get_data_from_user();
let data = initial_processing(data);
let data = further_processing(data);
if some_condition {
let data = conditional_processing(data);
} else {
let data = fallback_processing(data);
}
(也许答案是代码气味,我应该将if some_condition
函数调用内的conditional_processing
检查移到。)
因此,例如,可重现示例的一种可能的重写:
let mut x = 10;
if true {
x = 20;
}
我认为这与我正在考虑的做法相去甚远。
可以写
let x = 10;
let mut y = x;
if true {
y = 20;
}
let x = y;
println!("x is {}",x);
因此,x
最终是设置为20
的非可变变量,尽管以引入一次性中间可变变量y
为代价。但是我仍然很好奇是否可以通过捕获if
块并故意将变量隐藏在其外部来实现这一点。
解决方法
已更新(请参见下面的原始答案)
您可能会对
感兴趣let data = get_data_from_user();
let data = initial_processing(data);
let data = further_processing(data);
let data = if some_condition {
conditional_processing(data)
} else {
fallback_processing(data)
};
或者如果您想为else
保持相同的值
let x = 10;
let x = if true {
20
} else {
x
}
原始答案
不,这不可能。
- 您不能强制变量在定义块之外可见。因此
let x = <...>
无法正常工作。 - 您不能更改不可变变量的值。因此
x = <...>
无法正常工作。 - 没有其他方法可以将值分配给变量。
您可以通过重新绑定相同的变量来实现。
// first step,prepare x as mutable
let mut x = 10;
if true {
x = 20;
}
let x = x; // new binding for x
// from now on,x is immutable
表达相同想法的更常见(或可读)方式:
let x = {
// prepare a mutable x just inside this block
let mut x = 10;
if true {
x = 20;
}
x // the result of this whole block
};
// in this scope,x is immutable
这两种构造的共同点是您开始 带有可变绑定以将值初始化为多个 步骤,然后完成操作,切换到不可变绑定 具有相同的值,以防止意外 变异它。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。