如何在Dart 3中正确使用Comparable?

huangapple go评论71阅读模式
英文:

How to use Comparable correctly with Dart 3?

问题

在Dart 3中,您不能再将任何类用作mixin,也不能将接口类扩展到其库之外。为了迁移到Dart 3,您可以采用以下方法:

首先,移除mixin中的on Comparable<T>部分,因为Dart 3不再支持这样的用法。然后,将您的类改为实现Comparable<T>接口,而不是继承它。

下面是迁移后的代码示例:

mixin Compare<T> {
  bool operator <=(T other) => compareTo(other) <= 0;
  bool operator >=(T other) => compareTo(other) >= 0;
  bool operator <(T other) => compareTo(other) < 0;
  bool operator >(T other) => compareTo(other) > 0;
}

class Foo implements Comparable<Foo> with Compare<Foo> {
  final int value;

  const Foo({required this.value});

  @override
  int compareTo(Foo other) => value.compareTo(other.value);
}

通过这种方式,您不再将Comparable<Foo>用作mixin,而是将其用作接口,并且现在可以在Dart 3中正常工作了。

英文:

With Dart SDK 2.x.x. it was okay to use any class as mixin. But with Dart 3 this is no longer allowed as stated in the documentation: https://dart.dev/resources/dart-3-migration#mixin

Now I struggle with the migration. For example, I used the Comparable interface as mixin like this:

mixin Compare&lt;T&gt; on Comparable&lt;T&gt; {
  bool operator &lt;=(T other) =&gt; compareTo(other) &lt;= 0;
  bool operator &gt;=(T other) =&gt; compareTo(other) &gt;= 0;
  bool operator &lt;(T other) =&gt; compareTo(other) &lt; 0;
  bool operator &gt;(T other) =&gt; compareTo(other) &gt; 0;
}


class Foo with Comparable&lt;Foo&gt;, Compare&lt;Foo&gt; {
  final int value;

  const Foo({required this.value});
  
  @override
  int compareTo(Foo other) =&gt; value.compareTo(other.value);
}

But this gives me the error error: The class &#39;Comparable&#39; can&#39;t be used as a mixin because it&#39;s neither a mixin class nor a mixin.

But if I try to use it as interface like this

mixin Compare&lt;T&gt; on Comparable&lt;T&gt; {
  bool operator &lt;=(T other) =&gt; compareTo(other) &lt;= 0;
  bool operator &gt;=(T other) =&gt; compareTo(other) &gt;= 0;
  bool operator &lt;(T other) =&gt; compareTo(other) &lt; 0;
  bool operator &gt;(T other) =&gt; compareTo(other) &gt; 0;
}


class Foo extends Comparable&lt;Foo&gt; with Compare&lt;Foo&gt; {
  final int value;

  const Foo({required this.value});

  @override
  int compareTo(Foo other) =&gt; value.compareTo(other.value);
}

I get another error The class &#39;Comparable&#39; can&#39;t be extended outside of its library because it&#39;s an interface class.

So what is the best way to migrate my code to Dart 3?

答案1

得分: 1

以下是您要翻译的内容:

"你所试图实现的可以通过扩展来实现。

void main() {
  final a = Foo(value: 20);
  final b = Foo(value: 40);

  print(a > b);
}

extension Compare<T> on Comparable<T> {
  bool operator <=(T other) => compareTo(other) <= 0;
  bool operator >=(T other) => compareTo(other) >= 0;
  bool operator <(T other) => compareTo(other) < 0;
  bool operator >(T other) => compareTo(other) > 0;
}

class Foo implements Comparable<Foo> {
  final int value;

  const Foo({required this.value});

  @override
  int compareTo(Foo other) => value.compareTo(other.value);
}

如果您注释掉扩展代码,那么对于 print(a > b);,您将在编译时出现错误,因此根据Dart3,这是有效的代码。"

英文:

What you were trying to get can be achieved by extensions.

void main() {
  final a = Foo(value: 20);
  final b = Foo(value: 40);

  print(a &gt; b);
}

extension Compare&lt;T&gt; on Comparable&lt;T&gt; {
  bool operator &lt;=(T other) =&gt; compareTo(other) &lt;= 0;
  bool operator &gt;=(T other) =&gt; compareTo(other) &gt;= 0;
  bool operator &lt;(T other) =&gt; compareTo(other) &lt; 0;
  bool operator &gt;(T other) =&gt; compareTo(other) &gt; 0;
}

class Foo implements Comparable&lt;Foo&gt; {
  final int value;

  const Foo({required this.value});

  @override
  int compareTo(Foo other) =&gt; value.compareTo(other.value);
}

If you comment extension code, you will get compile time error for print(a &gt;b); hence this is valid code as per Dart3

答案2

得分: 1

@jamesdlin的评论回答了我的问题:

mixin Compare<T> implements Comparable<T> {
  bool operator <=(T other) => compareTo(other) <= 0;
  bool operator >=(T other) => compareTo(other) >= 0;
  bool operator <(T other) => compareTo(other) < 0;
  bool operator >(T other) => compareTo(other) > 0;
}

class Foo with Compare<Foo> {
  final int value;

  const Foo({required this.value});
  
  @override
  int compareTo(Foo other) => value.compareTo(other.value);
}

这就是为什么Compare可以是一个mixin。

英文:

The comment of @jamesdlin answers my question:

mixin Compare&lt;T&gt; implements Comparable&lt;T&gt; {
  bool operator &lt;=(T other) =&gt; compareTo(other) &lt;= 0;
  bool operator &gt;=(T other) =&gt; compareTo(other) &gt;= 0;
  bool operator &lt;(T other) =&gt; compareTo(other) &lt; 0;
  bool operator &gt;(T other) =&gt; compareTo(other) &gt; 0;
}


class Foo with Compare&lt;Foo&gt; {
  final int value;

  const Foo({required this.value});
  
  @override
  int compareTo(Foo other) =&gt; value.compareTo(other.value);
}

That why, Compare can be a mixin.

huangapple
  • 本文由 发表于 2023年5月11日 12:53:12
  • 转载请务必保留本文链接:https://go.coder-hub.com/76224247.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定