本文介绍了我该如何使许多不同的结构都实现相同的特征并相互比较?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

在Java语言中,我有一个interface R,一个interface RT extends R(其中RT实现了所有R)和一堆其他都实现了RT的类.

In Java-lingo, I have an interface R, an interface RT extends R (where RT implements all of R) and a bunch of other classes that all implement RT.

向Rust的过渡我有两个特征

Transitioning to Rust I ended up with two traits

trait R { ... }
trait RT { ... }

其中RTR的子特征":

impl R for X where X: RT { ... }

接着我有一堆结构,所有这些结构都实现了RT:

Following that I have a bunch of structs, all of which implement RT:

struct RV { ... }
impl RT for RV { ... }

struct I { ... }
impl RT for I { ... }

struct U { ... }
impl RT for U { ... }

// ...

到目前为止一切都很好.

So far so good.

现在,我希望所有这些结构在实现全部RT的基础上彼此具有可比性.

Now I want all of these structs to be comparable to each other, on the basis that all of them implement RT.

在Java中,我将RT更改为

In Java I would change RT to

interface RT extends R, Comparable<RT>

并为equalscompareTo添加默认实现.

在Rust中,我不知道是否或如何解决这个问题.

In Rust I have no idea if or how this could be approached.

我可以说trait RT: PartialEq,但这只会使一个实现与其自身具有可比性(RV == RV,但不能与RV == U相比).

I could say trait RT: PartialEq, but that would only make one implementation comparable with itself (RV == RV, but not RV == U).

我的下一个想法是为每个结构添加一揽子实现:

My next idea was to add blanket implementations for every struct:

impl PartialEq<RV> for X where X: RT
impl PartialEq<I> for X where X: RT
// ...

我理解为什么不允许这样做,但是我仍然会遇到最初的问题.

I understand why this isn't allowed, however I'm still stuck with my initial problem.

我无法转换比较值(RV as RT == U as RT),因为不能将RT制成对象.

I can't cast the values for comparison (RV as RT == U as RT) because RT can't be made into an object.

我可以为每种结构的组合手动实现PartialEq<T>,但这会造成很多重复.

I could manually implement PartialEq<T> for every combination of structs but that would be a lot of duplication.

我考虑过使用宏来生成所有不同的实现,但是感觉就像蛮力的,所以我质疑程序的初始设计.

I considered using a macro to generate all the different implementations, but that feels so much like brute-forcing, that I question the initial design of my program.

我如何使所有不同的结构彼此可比?

How do I make all the different structs comparable to each other?

推荐答案

这种模式通常出现在Java中,以模拟带标记的联合,而Java语言中缺少这种联合.在Rust中,除非您编写的库可能需要用户定义RT的新实现,否则我怀疑您会更喜欢使用enum而不是特征对象:

That pattern often arises in Java to emulate tagged unions, which are missing from the Java language. In Rust, unless you are writing a library whose users may need to define new implementations of RT, I suspect you’ll be happier with an enum instead of a trait object:

#[derive(PartialEq, Eq)]
enum AnyRT {
    RV(RV),
    I(I),
    U(U),
}

impl RT for AnyRT {
    fn foo(&self, ...) {
        match self {
            AnyRT::RV(rv) => rv.foo(...),
            AnyRT::I(i) => i.foo(...),
            AnyRT::U(u) => u.foo(...),
        }
    }
}

然后,根据您的应用程序,您可能会发现根本不需要RT特征和/或单独的RVIU结构.

Depending on your application, you may then find that you don’t need the RT trait and/or the separate RV, I, U structs at all.

这篇关于我该如何使许多不同的结构都实现相同的特征并相互比较?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

10-27 20:04