首页 > 解决方案 > 如何使用关联常量来定义数组的长度?

问题描述

我有一个特征,它代表一个可以通过 UDP 套接字发送的实体:

pub trait ToNetEnt {
    const NET_SIZE: usize;

    fn from_net(data: &[u8]) -> Self;
    fn to_net(&self) -> &[u8];
}

虽然有一个关联的常量NET_SIZE,但我不能在方法中使用它:

pub fn req<T: ToNetEnt>(&self) -> T {
    let buf: [u8; T::NET_SIZE];
}

因为它会导致此错误:

error[E0599]: no associated item named `NET_SIZE` found for type `T` in the current scope
  --> src/main.rs:10:23
   |
10 |         let buf: [u8; T::NET_SIZE];
   |                       ^^^^^^^^^^^ associated item not found in `T`
   |
   = help: items from traits can only be used if the trait is implemented and in scope
   = note: the following trait defines an item `NET_SIZE`, perhaps you need to implement it:
           candidate #1: `ToNetEnt`

我可以在这种情况下使用关联的常量吗?

标签: functionrusttraits

解决方案


在撰写本文时,这是不可能的。但让我们首先修复您的代码:

pub fn req<T: ToNetEnt>(&self) -> T {
    let buf: [u8; <T as ToNetEnt>::NET_SIZE];
    ...
}

操场

这应该是正确的语法,但目前无法编译:

error[E0277]: the trait bound `T: ToNetEnt` is not satisfied
 --> src/main.rs:6:19
  |
6 |     let buf: [u8; <T as ToNetEnt>::NET_SIZE];
  |                   ^^^^^^^^^^^^^^^^^^^^^^^^^ the trait `ToNetEnt` is not implemented for `T`
  |
  = help: consider adding a `where T: ToNetEnt` bound

这只是问题的错误错误消息。在 GitHub 上查看此评论

[U] 将关联的 const 用作数组大小似乎不起作用:

pub trait Can {
    const SIZE: usize;
}

fn f<T: Can>(t: T) {
    // error[E0277]: the trait bound `T: Can` is not satisfied
    let x = [0u8; <T as Can>::SIZE];
}

错误消息显然是错误的,因此这要么是错误,要么是rustc未实现的功能导致虚假错误消息。

您可以const NET_SIZE在直接在结构中定义时解决此问题。

您可以在 GitHub 问题上阅读有关此特定错误的更多信息:数组长度不支持泛型类型参数 (#43408)


推荐阅读