如何在方法 impl 中从枚举中的字符串返回 &str ? [英] How can I return a &str from Strings in an enum in a method impl?

查看:55
本文介绍了如何在方法 impl 中从枚举中的字符串返回 &str ?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想返回城市/城镇/村庄的名称作为对 str 的引用.我可以在实现中指定生命周期,但也为枚举指定它会导致错误,因为它没有声明引用.

I want to return the name of the city/town/village as a reference to str. I can specify the lifetime in the implementation but specifying it also for the enum causes error as it has no reference declared.

enum CityType {
    City { name: String /* ... */ },
    Town { name: String /* ... */ },
    Village { name: String /* ... */ },
}

impl CityType {
    fn name(self) -> &str {
        match self {
            CityType::City { name } => &name,
            CityType::Town { name, .. } => &name,
            CityType::Village { name } => &name,
        }
    }
}

游乐场

推荐答案

如果你只是想返回一个城市名称不会因为消费而丢失对象,那么你应该这样写:>

If you just want to return a city name without losing the object by consuming, you should write it as the following:

enum CityType {
    City { name: String },
    Town { name: String },
    Village { name: String },
}

impl CityType {
    fn name(&self) -> &str {
        match *self {
            CityType::City { ref name } => name,
            CityType::Town { ref name, .. } => name,
            CityType::Village { ref name } => name,
        }
    }
}

fn main() {
    let city = CityType::City { name: "NY".to_owned() };
    println!("Name of the city: {}", city.name());
}

说明:

  1. 首先,您的方法的签名指定您使用对象:

fn name(self) -> &str {

调用这样的方法后,您将无法再使用该实例.如果你想读取一个字符串,你应该接受一个引用:

After calling such a method, you will no longer be able to use the instance. If you want to read a string, you should accept a reference:

fn name(&self) -> &str {

这会导致另一个问题

match 应该可以在不移动对象的情况下工作,所以这里是 *:

match should work without moving an object, so here is *:

match *self {

  • 你不应该从枚举的数据中移出,所以 ref 关键字有帮助

    CityType::City { ref name } => name,
    

    这个关键字表示我们必须使用带有值引用的模式匹配.

    This keyword says that we must use pattern matching with a reference to value.

    main 中,您传递了 &str 但枚举中的项目是 String,因此这会导致类型不兼容错误.通过对字符串引用调用 .to_owned() 方法,您可以从中创建一个新的 String 对象:

    In the main you pass a &str but items in your enum are String, so this lead to incompatible types error. By calling .to_owned() method on a string reference you create a new String object from it:

    let city = CityType::City { name: "NY".to_owned() };
    

  • 供您评论:

    问题更普遍:如何将 ref 返回给没有生命周期说明符的字符串,因为它的生命周期与枚举一样长.

    The issue is more general: how to return ref to a String which has no lifetime specifier as it lives as long as the enum does.

    在 Rust 中,你不能拥有一个没有生命周期的引用.绝不.在某些情况下,编译器可以为您推断生命周期,但也有一些情况下它不正确或不符合您的预期.在这种情况下,例如:

    In Rust you can't have a reference without a lifetime. Never. There are cases in which the compiler can deduce the lifetime for you, but there are also cases when it does it incorrectly or not what you expected. In this case, for example:

    fn name(&self) -> &str {
    

    个生命周期,编译器将其视为以下内容:

    There are lifetimes, the compiler treats this as the following:

    fn name<'a>(&'a self) -> &'a str {
    

    您的引用绑定到相同的生命周期并且可以使用.

    Your references are bound to the same lifetime and they can be used.

    这篇关于如何在方法 impl 中从枚举中的字符串返回 &amp;str ?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

    查看全文
    登录 关闭
    扫码关注1秒登录
    发送“验证码”获取 | 15天全站免登陆