Определение собственного типа данных в предложении Haskell Где - PullRequest
1 голос
/ 03 февраля 2020
data Geometry = Point {xCoord:: Double
                        ,yCoord:: Double} |Line  {xCoeff:: Double 
                      ,yCoeff:: Double
                       ,constant:: Double}|Plane {xCoeff:: Double,yCoeff:: Double, 
                       zCoeff::Double,
                       constant::Double} deriving (Show)

intersection:: Geometry -> Geometry -> Either String Geometry
intersection (Line a1 b1 c1) (Line a2 b2 c2)
                              | #### some code

intersection (Plane a1 b1 c1 d1) (Plane a2 b2 c2 d2)
                               | #### some code
                               | n1_n2_z /= 0 = Right $ParamerticLine (Point3D t1 (cond12/n1_n2_z) 0) (Point3D n1_n2_x n1_n2_y n1_n2_z)
                               | otherwise ## some code
                               where {Point t1 t2 = intersection (Line a1 b1 d1) (Line a2 b2 d2)}

Я пытаюсь вычислить пересечение линии, где пункт пересечения плоскости, и используя t1 в условии n1_n2_z / = 0. Я получаю сообщение об ошибке для пункта where. Могу ли я использовать функцию пересечения, как определено в предложении where. Что я делаю не так в предложении where?

1 Ответ

1 голос
/ 03 февраля 2020

Причина, по которой это не удается, заключается в том, что intersect имеет в качестве подписи:

intersection:: Geometry -> Geometry -> <b>Either String Geometry</b>

, но в левой части предложения where написано:

where <b>Point</b> t1 t2 = intersection (Line a1 b1 d1) (Line a2 b2 d2)

, поэтому здесь левый операнд имеет тип Geometry, а не Either String Geometry.

Вы должны записать это как:

where <b>Right (</b>Point t1 t2<b>)</b> = intersection (Line a1 b1 d1) (Line a2 b2 d2)

Но это небезопасно , так как может случиться так, что это «оставленное» сообщение об ошибке ». Таким образом, вы можете использовать паттерн [Haskell -wiki] здесь:

# &hellip;
intersection (Plane a1 b1 c1 d1) (Plane a2 b2 c2 d2)
    | &hellip; = &hellip;
    | n1_n2_z /= 0, <b>Right (Point t1 t2) <-</b> intersection (Line a1 b1 d1) (Line a2 b2 d2) = Right $ ParamerticLine (Point3D t1 (cond12/n1_n2_z) 0) (Point3D n1_n2_x n1_n2_y n1_n2_z)
    | otherwise = &hellip;

Или вы можете взглянуть на Monad (Either a) реализации, и, следовательно, использовать привязку для работы с такими Either a.

...