standard ml make bst out of a list

半腔热情 提交于 2019-12-25 03:32:55

问题


I want to make a function standard ml that takes a list and function and makes a BST out of it. The function's type is: 'a list -> ('a * 'a -> bool) -> 'a tree, but I'm having some problems with it, here are the code I wrote:

datatype 'data tree = 
  EMPTY
| NODE of 'data tree * 'data * "data tree;

fun makeBST [] f = EMPTY
  | makeBST (x::xs) f = 
     let
        fun insert EMPTY x = NODE(EMPTY, x, EMPTY)
          | insert (NODE(left, root, right)) x = 
                if f(x, root) then
                    insert left x
                else
                    insert right x
     in 
        makeBST xs f
     end;

The type i'm getting with this function is: 'a list -> ('b * 'c -> bool) -> 'd tree and when I try to call it, like the following makeBST [4, 3, 6, 7, 8, 2, 0, 1] (op <); I get the following error:

stdIn:16.1-16.40 Warning: type vars not generalized because of
   value restriction are instantiated to dummy types (X1,X2,...)
val it = EMPTY : ?.X1 tree

What is wrong with the code? Thanks

EDIT:

Second version of my code:

fun makeBST [] f = EMPTY
    | makeBST (x::xs) f = 
        let
            val tree = EMPTY
            fun insert EMPTY x = NODE (EMPTY, x, EMPTY)
              | insert (NODE(left, root, right)) x = 
                    if f(x, root) then
                        insert left x
                    else
                        insert right x
        in
            insert (makeBST xs f) x
        end;

This code produced the type i want but is it correct?


回答1:


Two problems with the first version of your code:

  • You're declaring a function in your let block which is never used, and your function recursively calls itself until the first argument is an empty list, so your code can be simplified to fun makeBST _ _ = EMPTY, so this is probably the reason for the error you're receiving because SML doesn't know what type EMPTY is supposed to be.
  • Double quotes on line 3 which should be a single quote

Though, since you've made a second version, I'm guessing you caught this already. Your new code still isn't correct yet though. The result of any call to this function is a tree with the first element of the list as a root and two EMPTY children. You're comparing the left and right subtree and then adding the new value at the right place, but the issue is that you only return that subtree and not the entire tree. What you want is the following:

fun makeBST [] f = EMPTY
    | makeBST (x::xs) f = 
        let
            val tree = EMPTY
            fun insert EMPTY x = NODE (EMPTY, x, EMPTY)
              | insert (NODE(left, root, right)) x = 
                    if f(x, root) then
                        Node(insert left x, root, right)
                    else
                        Node(left, root, insert right x)
        in
            insert (makeBST xs f) x
        end;


来源:https://stackoverflow.com/questions/9954177/standard-ml-make-bst-out-of-a-list

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!