2015-02-15 3 views
3

У меня есть 2 типа, Дерево и BinTree. Путь я реализую сравнить это так:Сравнение 2 подобных типов?

Как вы можете видеть, моя функция следы счастлив работать как на дереве и BinTree, таким образом, должен быть способ для меня, чтобы сделать: myBinTree < myTree

Таким образом, сравнивая BinTree с дерева

Как один идти о реализации этого так, что BinTrees и деревья можно сравнить, так как BinTree подмножество дерева.

+2

Вы можете [преобразовать 'BinTree' в' Tree'] (http://stackoverflow.com/questions/28511329/converting-a-binarytree-to-a-tree) и сравнить 'Tree'. – Cirdec

+0

@Cirdec Да, но есть ли способ сделать это так, чтобы я мог использовать оператор < jmasterx

+1

Нет, ['<' имеет тип 'Ord a => a -> a -> Bool'] (http://hackage.haskell.org/packages/archive/base/latest/doc/html/Prelude.html #v: -60-). Два аргумента должны быть одного типа. – Cirdec

ответ

5

Не так, чтобы стать экземпляром классов Eq или Ord. Эти классы имеют подпись:

(==) :: a -> a -> Bool 
(/=) :: a -> a -> Bool 

и так далее ...

Вы можете написать свою собственную (==) функцию, но тогда эта функция становится неоднозначной, и в результате вы всегда должны указать, о которых (==) оператор, о котором вы говорите.

Ответ на ваш комментарий «Как haskell сравнивает поплавки с целыми числами?« это не так. Если вы пишете:

> (1 :: Int) == (1.0 :: Float) 

<interactive>:56:16: 
    Couldn't match expected type `Int' with actual type `Float' 
    In the second argument of `(==)', namely `(1.0 :: Float)' 
    In the expression: (1 :: Int) == (1.0 :: Float) 
    In an equation for `it': it = (1 :: Int) == (1.0 :: Float) 

Вы видите, что сравнение невозможно. Вы можете сделать это путем преобразования:

> fromIntegral (1 :: Int) == (1.0 :: Float) 
True 

Где fromIntegral это функция, которая преобразует Int в - в данном случае - Float. Вы можете сделать то же самое, выполнив функцию bin2tree.

Вы, конечно, можете определить свой собственный подобный класс:

class Similar a b where 
    (=~) :: a -> b -> Bool 
    (/=~) :: a -> b -> Bool 
    (/=~) x y = not $ x =~ y 

(и добавить {-# LANGUAGE MultiParamTypeClasses #-} в файл в качестве модификатора).

А потом, например:

instance (Similar a b) => Similar [a] [b] where 
    (=~) [] [] = True 
    (=~) _ [] = False 
    (=~) [] _ = True 
    (=~) (x:xs) (y:ys) = (x =~ y) && (xs =~ ys) 

Но проблема в том, что вам придется пересмотреть много методов себя (которые принимают использование Eq как nub) таким образом, что они работают с Similar класса.

Смежные вопросы