编译器:rustc 1.71.0-nightly (c609da59d 2023-04-18)
我每晚都尝试#![feature(try_blocks)]这样做:
#![feature(try_blocks)]
fn test_try(input: Option<i32>) {
let output = try {
input?
};
println!("{:?}", output);
}
Run Code Online (Sandbox Code Playgroud)
但编译器声称output需要类型注释。完整的错误消息在这里:
error[E0282]: type annotations needed
--> src/main.rs:3:9
|
3 | let output = try {
| ^^^^^^
|
help: consider giving `output` an explicit type
|
3 | let output: /* Type */ = try {
| ++++++++++++
Run Code Online (Sandbox Code Playgroud)
如果我尝试let output: Option<i32> = ...一切正常。
看起来output应该是,Option<i32>但编译器并没有推断出这一点。
仅仅是因为该功能不稳定还是我错过了什么?除 之外还有其他类型Option<i32>吗output?
try_blocks由于推理问题,该特征大多不稳定。特征的设计Try(为try块和?运算符提供动力)使其非常灵活,但编译器也很难推断类型。
Option<i32>在 std 中,除了可以是该表达式的结果之外,没有任何其他内容。但是我们可以写一个,因为驱动块脱糖的try不是?其中编辑的类型,而是它产生的类型。所以它可以是任何东西,只要它支持?ing Option<i32>。例如:
#![feature(try_blocks, try_trait_v2)]
use std::convert::Infallible;
use std::ops::ControlFlow;
#[derive(Debug)]
struct MyFancyType;
impl std::ops::FromResidual<Option<Infallible>> for MyFancyType {
fn from_residual(_residual: Option<Infallible>) -> Self {
Self
}
}
impl std::ops::FromResidual for MyFancyType {
fn from_residual(_residual: Infallible) -> Self {
Self
}
}
impl std::ops::Try for MyFancyType {
type Output = i32;
type Residual = Infallible;
fn from_output(_output: i32) -> Self {
Self
}
fn branch(self) -> ControlFlow<Self::Residual, Self::Output> {
ControlFlow::Continue(0)
}
}
fn test_try(input: Option<i32>) {
let output: MyFancyType = try { input? };
println!("{:?}", output);
}
Run Code Online (Sandbox Code Playgroud)
游乐场。