关于 IndexOf 过度实现的问题

发布于 2024-07-10 13:26:07 字数 1589 浏览 7 评论 0原文

我有一个 C# 优先级队列实现,我想向其中添加 .IndexOf 方法。

然而,由于优先级队列并不真正关心值本身的顺序(也就是说,如果我只是获取所有值,忽略它们的优先级,它们根本不一定有任何顺序),只对于它们的优先级,我对优先级队列的通用类型 T 没有任何标准,也就是说,我没有指定它们需要具有某种内在顺序或可比性。

因此,当我实现 .IndexOf(T value) 时,我遇到了一个小问题。

我应该执行什么/如何执行此操作有一个标准吗? 我最初的想法只是使用 EqualityComparer.Default 来确定我是否找到了 value ,但现在有很多类似的此类类型。

例如,以下是我想出的内容来涵盖我的基础,但这似乎有点过头了:

  • public Int32 IndexOf(T value)(在内部使用ClassThatImplementsInterface.Default调用其他之一) >)
  • public Int32 IndexOf(T 值,IComparer比较器)
  • public Int32 IndexOf(T 值,IEqualityComparer比较器)
  • public Int32 IndexOf(T value, IEquatable比较器)
  • public Int32 IndexOf(T value, Predicatepredicate)

你做什么? 将其标记为主观和维基,因为这更像是一次民意调查。

在重新阅读我自己的问题时,我想我可以只使用没有比较器的版本,然后添加谓词版本,这样该类的用户就可以调用任何内容。

另请注意,我还可以执行 pq[index] 来获取包含优先级和值本身的项目,因此我也可以完全不使用 IndexOf,但我也可以喜欢有这样的方法:将值 X 的优先级更改为优先级 P,这在内部需要某种形式的 IndexOf/search。 因此,我也想避免所有这些方法的无数次重载。


回复评论:是的,优先级队列是基于堆的。

基本上,这两个类的定义如下:

public class Heap<T> : IEnumerable<T>, ICloneable { ... }
public class PriorityQueue<T> : Heap<PriorityQueueElement<T>> { ... }

PriorityQueueElement 是一个简单的不可变结构,具有 Priority 和 Value 属性。

对即将发表的评论的回应:由于优先级队列是基于堆的,因此一个“有趣的属性”是,通过索引更改值的优先级意味着之后,该值不一定会被更改。在该索引处。 我打算只是记录这一点,因为在某些情况下我预见需要独立的定位/更改优先级操作。

I have a priority queue implementation in C# that I want to add a .IndexOf method to.

However, since the priority queue doesn't really concern itself with the order of the values themselves (that is, if I were to just grab all the values, disregarding their priorities, they wouldn't necessarily have any order at all), only the priority of them, I don't have any criteria for the generic type T of the priority queue, that is, I don't specify that they need to have some intrinsic order, or comparability.

As such, when I came to implement .IndexOf(T value) I have a minor problem.

Is there a standard in what/how I should implement this? My initial thoughts was simply to use EqualityComparer<T>.Default to figure if I have found the value or not, but then there are so many similar such types these days.

For instance, here's what I came up with to cover my basis, but this seems overkill:

  • public Int32 IndexOf(T value) (internally calls one of the others with ClassThatImplementsInterface.Default)
  • public Int32 IndexOf(T value, IComparer<T> comparer)
  • public Int32 IndexOf(T value, IEqualityComparer<T> comparer)
  • public Int32 IndexOf(T value, IEquatable<T> comparer)
  • public Int32 IndexOf(T value, Predicate<T> predicate)

What do you do? Marking this as both subjective and wiki as this is more of an opinion poll than anything else.

On re-reading my own question I guess I can just use the one without a comparer, and then add the predicate version, this way the user of this class can call just about anything.

Also note that I can also do pq[index] to get hold of a item that contains both the priority and the value itself, so I could also get by without IndexOf at all, but I'd also like to have methods that says change the priority of value X to priority P, which would necessitate some form of IndexOf/search internally. And thus I'd also like to avoid having to have umpteenth overloads of all these methods as well.


Response to comment: Yes, the priority queue is based on a heap.

Basically, the two classes are defined like this:

public class Heap<T> : IEnumerable<T>, ICloneable { ... }
public class PriorityQueue<T> : Heap<PriorityQueueElement<T>> { ... }

PriorityQueueElement is a simple immutable structure with Priority and Value properties.

Response to forthcoming comment: Since the priority queue is based on a heap, an "interesting property" is that by changing the priority of a value through its index means that afterwards, the value won't necessarily be at that index. I intend to just document this as in some cases I foresee a need for independent locate/change-priority operations.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

夏九 2024-07-17 13:26:07

我会将比较作为可选的构造函数参数; 这类似于 Dictionary<,>SortedList<,> 等允许您指定比较机制的方式。

是否接受 IComparer 还是 IEqualityComparer 取决于您是要对数据进行排序,还是只是查找相等匹配; 如果匹配,那么您将需要类似 IEqualityComparer 的内容。 不幸的是,由于它有 2 个方法(GetHashCode()Equals()),所以没有直接的委托版本,除了 PredicateFunc

对于默认构造函数,我将传入 [Equality]Comparer.Default

I would make the comparison an optional constructor parameter; this is comparable to how things like Dictionary<,>, SortedList<,> etc allow you to specify the comparison mechanism.

Whether to accepts an IComparer<T> or an IEqualityComparer<T> depends on whether you are going to sort the data, or just look for an equality match; if the match, then you'll need something like IEqualityComparer<T>. Unfortunately, since this has 2 methods (GetHashCode() and Equals()) there is no direct delegate version of this, except perhaps Predicate<T> or Func<T,T,bool>.

For the default constructor, I'd pass in the [Equality]Comparer<T>.Default.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文