Rust 即使临时数组包含也具有静态生存期的值,也无法返回对该数组的静态引用
从Rust 即使临时数组包含也具有静态生存期的值,也无法返回对该数组的静态引用,rust,Rust,从T::bar返回的值具有的静态寿命,因此Test2::foo范围不需要拥有任何内容。将&[T::bar()]作为&'static[&'static StructType]返回应该是安全的吗测试:foo编译没有问题,所以我希望Test2::foo也能编译 代码 我认为你对人生的看法是错误的。看起来你用它们来“声明”你想要它活多久,但是你不能改变引用的生存期。所有的生命周期说明符都是为了帮助编译器在没有信息省略生命周期的情况下理解生命周期 我应该帮你 基本上,只有两种方法可以创建静态数据: 使用s
T::bar
返回的值具有的静态寿命,因此Test2::foo
范围不需要拥有任何内容。将&[T::bar()]
作为&'static[&'static StructType]
返回应该是安全的吗<代码>测试:foo
编译没有问题,所以我希望Test2::foo
也能编译
代码
我认为你对人生的看法是错误的。看起来你用它们来“声明”你想要它活多久,但是你不能改变引用的生存期。所有的生命周期说明符都是为了帮助编译器在没有信息省略生命周期的情况下理解生命周期 我应该帮你 基本上,只有两种方法可以创建静态数据:
static
声明创建一个常量&'static str
静态的生命周期,因为您自己没有声明任何生命周期)。见下文
主要的一点是,除了&'static str
,生命周期永远不能通过在函数中注释生命周期来改变。当您编写&[T::bar()]
时,数组不是一个常量,当您离开作用域时,如果您使用函数,数组将被删除。如果你想让它有一个静态的生命周期,你需要让它成为一个常量,就像我在下面展示的那样
现在,这可能不是您想要做的,但它将编译,我希望能解释其中的区别:
const ARR: &'static [&'static StructType] = &[&StructType { a: "asdf" }];
pub struct StructType {
a: &'static str,
}
pub trait Foo<'a> {
fn foo() -> &'a [&'a StructType];
fn bar() -> &'a StructType;
}
pub struct Test;
impl<'a> Foo<'a> for Test {
fn foo() -> &'a [&'a StructType] {
&[&StructType { a: "asdf" }]
}
fn bar() -> &'a StructType {
&StructType { a: "asdf" }
}
}
pub struct Test2<T: Foo<'static>>(T);
impl<T: Foo<'static>> Test2<T> {
pub fn foo() -> &'static [&'static StructType] {
ARR
}
}
const ARR:&'static[&'static StructType]=&[&StructType{a:“asdf”}];
发布结构类型{
答:&',
}
用于测试的pub-Foo{
fn foo()->&'a[&'a StructType]{
&[&StructType{a:“asdf”}]
}
fn bar()->&'a StructType{
&结构类型{a:“asdf”}
}
}
发布结构Test2>Test2{
pub fn foo()->&'static[&'static StructType]{
啊
}
}
国家:
将constexpr rvalue提升为静态内存中的值,而不是堆栈插槽中的值,并通过能够直接创建对它们的“静态引用”来公开语言中的值
文字值是最明显的常量表达式。但是,函数调用不是常量,除非使用const
显式标记为常量。但是,从Rust 1.31开始,用户定义的const
函数中可用的操作类型相当有限。允许使用文字值:
const fn bar() -> &'static StructType {
&StructType("asdf")
}
const fn combo() -> &'static [&'static StructType; 1] {
&[Self::bar()]
}
在const
函数中还不允许从对数组的引用转换为切片,因此需要在不同的函数中进行转换:
fn wombo() -> &'static [&'static StructType] {
Self::combo()
}
此外,不能在trait中定义const
函数
另见:
我真正需要的是1)让T::bar()
返回一个常量,2)让Test:foo
返回一个数组常量,该数组常量由T::bar()
和U::bar()
和U
构成,T
是Test
的通用参数
你不能这样做
fn example<T>() {
static NO_CAN_DO: T = unimplemented!();
}
fn示例(){
静态NO_CAN_DO:T=未实现!();
}
错误[E0401]:无法使用外部函数中的类型参数
-->src/lib.rs:2:23
|
1 | fn示例(){
|----外部函数中的类型变量
| |
|请尝试在此方法中添加本地类型参数
2 |静态NO_CAN_DO:T=未实现!();
|^使用外部函数中的类型变量
另见:
没关系,这是因为T::bar()
不是一个常量函数,所以数组不是常量,所以数组是在运行时构造的。也许你可以使用const函数的夜间功能。看起来trait不可能有const函数,@Stargateur我明白你的意思。Test::foo
的数组只包含常量,因此可以采取静态生命来自它的ime引用。但是对于Test2:foo
它必须计算一些非常量表达式,这些表达式使数组非常量,因此不能从中获取静态生命周期引用。这是对的吗?我认为是的,可能需要等待一些其他意见,因为我还不是生锈专家;)可能重复感谢您的回答。但是幸运的是,您的示例没有多大帮助。我知道如何使某些内容进行编译。但我想知道当前的Rust编译器是否可以支持我的用例。(例如,返回包含某个方法调用结果的数组的静态引用)我也不明白为什么使用一个通用的生命周期参数会有任何帮助。我需要支持的只是'static
。Const函数很快就会生锈,但我认为这不会有什么不同(如果我正确理解你的问题的话)。问题是,你创建的数组只能使用到该函数的末尾(此时将释放该内存),即使数组包含静态数据。因此,您需要创建一个静态数组,并且该数组必须是常量。泛型生存期没有帮助,但在本例中,将它们声明为静态也没有任何意义,因此只是将“用于某个目的的静态”与那些同样可以作为泛型参数的静态分开。@BryanChen co现在可能是这样,但由于您没有提供为什么需要它,我很难猜到您需要什么。可能是我误解了这个问题,如果是这样,我很抱歉,但是您希望作为静态的方法调用需要在编译时知道(这里是因为您只存储静态字符串)但您仍然需要将其声明为const…如果您在这里查看const函数,可能这就是您要查找的
fn example<T>() {
static NO_CAN_DO: T = unimplemented!();
}