函数参数不满足特征界限
Trait bound not satisfied in function argument
我 运行 遇到了特征边界问题,无法理解我做错了什么。我正在使用来自 avr-hal 的 arduino-uno crate,我有一个读取 ADC 的函数,实现如下:
fn read_signal<T: avr_hal_generic::hal::adc::Channel<board::adc::Adc, ID = u8>>(
adc: &mut board::adc::Adc,
pinA0: &mut T,
) {
let x = adc.read(&mut pinA0);
}
但是,我收到以下错误:
the trait bound `&mut T: avr_hal_generic::embedded_hal::adc::Channel<arduino_uno::adc::Adc>` is not satisfied
required because of the requirements on the impl of `arduino_uno::prelude::_embedded_hal_adc_OneShot<arduino_uno::adc::Adc, _, &mut T>` for `arduino_uno::adc::Adc` rustc(E0277)
我试过使用 where
代替,但这没有帮助。我该如何解决这个问题?
另外,虽然我展示了这个具体的例子,但我真的很感激解释或指向关于这个 subject/error 的更好文档的指针,因为我遇到过几次并且很难理解哪里出了问题。
编译器错误说:
the trait bound &mut T: avr_hal_generic::embedded_hal::adc::Channel<arduino_uno::adc::Adc>
is not satisfied
请注意,错误要求 &mut T
实现 Channel
、&mut T: Channel<...>
,而您的 T
具有约束 T: Channel<...>
— 应用于 T
本身而不是 &mut T
。这就是为什么你已经写的界限没有帮助。
现在,正确的解决方法是什么?如果我查看您链接的文档,我可以找到 <Adc as OneShot>::read
的类型。 (注意:我从 docs 中复制了文本来构建此片段;我没有阅读源代码。)
impl<WORD, PIN> OneShot<Adc, WORD, PIN> for Adc
where
WORD: From<u16>,
PIN: Channel<Adc, ID = MUX_A>, // <---- look here
{
pub fn read(
&mut self,
_pin: &mut PIN // <---- look here
) -> Result<WORD, ...>
}
因此,read
应该被赋予 &mut PIN
并且类型变量 PIN
应该实现 Channel
。这一切听起来都很合理,但是在您的代码中 编译器认为我们希望&mut T
实现Channel
。出现了额外的 &mut
。它从哪里来的?您写道:
fn read_signal<T: avr_hal_generic::hal::adc::Channel<board::adc::Adc, ID = u8>>(
adc: &mut board::adc::Adc,
pinA0: &mut T,
) {
let x = adc.read(&mut pinA0);
}
pinA0
是 &mut T
类型,但是你写了 adc.read(&mut pinA0)
,这意味着 read()
的参数是 &mut &mut T
类型。由于 read
想要 &mut
实现 Channel
的东西,这会导致您看到的错误,要求 &mut T: Channel
.
然后,解决方法是不使用 &mut
of &mut
:
let x = adc.read(pinA0);
在某些情况下,Rust 提供 implicit coercions,特别是,它会将对引用的引用(或对实现 Deref
的 'smart pointer' 类型的引用)转换为引用.这就是为什么您过去可能有过无关的 &
或 &mut
工作。然而,当没有一个预期的具体类型时,这些强制转换不会被应用,例如在这种情况下,函数参数的类型包含类型变量 T
.
我 运行 遇到了特征边界问题,无法理解我做错了什么。我正在使用来自 avr-hal 的 arduino-uno crate,我有一个读取 ADC 的函数,实现如下:
fn read_signal<T: avr_hal_generic::hal::adc::Channel<board::adc::Adc, ID = u8>>(
adc: &mut board::adc::Adc,
pinA0: &mut T,
) {
let x = adc.read(&mut pinA0);
}
但是,我收到以下错误:
the trait bound `&mut T: avr_hal_generic::embedded_hal::adc::Channel<arduino_uno::adc::Adc>` is not satisfied
required because of the requirements on the impl of `arduino_uno::prelude::_embedded_hal_adc_OneShot<arduino_uno::adc::Adc, _, &mut T>` for `arduino_uno::adc::Adc` rustc(E0277)
我试过使用 where
代替,但这没有帮助。我该如何解决这个问题?
另外,虽然我展示了这个具体的例子,但我真的很感激解释或指向关于这个 subject/error 的更好文档的指针,因为我遇到过几次并且很难理解哪里出了问题。
编译器错误说:
the trait bound
&mut T: avr_hal_generic::embedded_hal::adc::Channel<arduino_uno::adc::Adc>
is not satisfied
请注意,错误要求 &mut T
实现 Channel
、&mut T: Channel<...>
,而您的 T
具有约束 T: Channel<...>
— 应用于 T
本身而不是 &mut T
。这就是为什么你已经写的界限没有帮助。
现在,正确的解决方法是什么?如果我查看您链接的文档,我可以找到 <Adc as OneShot>::read
的类型。 (注意:我从 docs 中复制了文本来构建此片段;我没有阅读源代码。)
impl<WORD, PIN> OneShot<Adc, WORD, PIN> for Adc
where
WORD: From<u16>,
PIN: Channel<Adc, ID = MUX_A>, // <---- look here
{
pub fn read(
&mut self,
_pin: &mut PIN // <---- look here
) -> Result<WORD, ...>
}
因此,read
应该被赋予 &mut PIN
并且类型变量 PIN
应该实现 Channel
。这一切听起来都很合理,但是在您的代码中 编译器认为我们希望&mut T
实现Channel
。出现了额外的 &mut
。它从哪里来的?您写道:
fn read_signal<T: avr_hal_generic::hal::adc::Channel<board::adc::Adc, ID = u8>>(
adc: &mut board::adc::Adc,
pinA0: &mut T,
) {
let x = adc.read(&mut pinA0);
}
pinA0
是 &mut T
类型,但是你写了 adc.read(&mut pinA0)
,这意味着 read()
的参数是 &mut &mut T
类型。由于 read
想要 &mut
实现 Channel
的东西,这会导致您看到的错误,要求 &mut T: Channel
.
然后,解决方法是不使用 &mut
of &mut
:
let x = adc.read(pinA0);
在某些情况下,Rust 提供 implicit coercions,特别是,它会将对引用的引用(或对实现 Deref
的 'smart pointer' 类型的引用)转换为引用.这就是为什么您过去可能有过无关的 &
或 &mut
工作。然而,当没有一个预期的具体类型时,这些强制转换不会被应用,例如在这种情况下,函数参数的类型包含类型变量 T
.