【问题标题】:Is there a better way to construct such a priority queue?有没有更好的方法来构建这样一个优先级队列?
【发布时间】:2013-03-13 08:51:44
【问题描述】:

我已经实现了一个优先队列,它运行良好。下面是我的类型定义。

type 'a t = | Leaf of ('a -> 'a -> int)
            | Node of 'a * 'a t * 'a t * ('a -> 'a -> int)

我的想法是树接受一个比较器函数('a -> 'a -> int)并产生一个'a t,它将由比较器排序。
但是,我在每个 Leaf 和 Node 上都有比较器,我想知道是否有更好的方法。
具体来说,给定一棵树,我希望能够轻松访问它的比较器。而且我不知道如果我的树的每个节点和叶子上没有比较器,我是否可以做到这一点。

谢谢

【问题讨论】:

    标签: tree functional-programming ocaml priority-queue


    【解决方案1】:

    解决这个问题的标准方法是编写一个给定的函子 一个模块,其中包含 PQ 中包含的类型 + 比较 您给出的函数返回一个专门用于该类型的新 PQ 模块 和比较功能。

    module PriorityQueue (OT : Map.OrderedType) = struct
      type t = 
        | Leaf
        | Node of OT.t * t * t
      (*Define your functions in terms of OT.compare ...*)
    end
    

    然后您将创建一个具体的 PriorityQueue 模块

    module FunnyPQ = PriorityQueue(struct
      type t = int
      let compare _ _ = pred (Random.int 3)
    end)
    

    查看 OrderedType 的定义:http://caml.inria.fr/pub/docs/manual-ocaml-4.00/libref/Map.OrderedType.html

    您当然也可以使用您已采取但不考虑因素的方法 将数据类型分为以下两种方式

    type 'a pq = 
      | Leaf
      | Node of 'a * 'a pq * 'a pq
    
    type 'a t = { 
      comp : 'a -> 'a -> int ;
      pq : 'a pq
    }
    

    请注意,您使用这种方法会失去一些类型安全性,因为现在如果您正在编写带有 'a pq -> 'a pq -> 'a pq 之类签名的函数,您不能保证第一个 pq 参数和第二个 pq 参数是使用相同的比较函数构造的.

    【讨论】:

    • 仿函数确实有效,但我认为比较器函数已经指示了树的类型,所以我不希望创建一个同时具有类型和函数的仿函数。
    • 我认为您的代码可能有问题。在第二个定义中,您的 pq 需要先定义 'a t,在 'a t 中,需要先定义 pq。我无法按照你的方式定义类型。
    • 这些定义并不意味着相互依赖。这与他关于使用与最初用于构建树的比较器函数不同的比较器函数的评论相称。
    • @nlucaroni :对不起,但我确实希望比较器在一棵树中保持一致。用户提供比较器的唯一方法是构建一个 Leaf 作为基本案例。
    • @didierc : 我不知道添加这样一个独立的结构是否值得。现在编辑的'a t 似乎是一个很好的结构。我试试看。
    猜你喜欢
    • 1970-01-01
    • 2010-12-15
    • 1970-01-01
    • 2023-04-02
    • 1970-01-01
    • 2010-10-01
    • 1970-01-01
    • 1970-01-01
    • 2023-04-08
    相关资源
    最近更新 更多