2016-11-30 33 views
-2

我想實現在Haskell如下:省略數據類型構造

0,1,2,...:N 
x,y,z,...:V 
+,*,-,/,...:F  
F alias for Expr -> Expr -> Expr 
Expr := N|V|F Expr Expr 

我的問題是第一:
是語法缺陷的類型級別?它有道理嗎?所有的條款看起來像他們會檢查(允許0,1,...既是Expr也是N子類型,並且x,y,...都是Expr和V子類型)。

其次,什麼是最接近Haskell的實現?我目前的Haskell實現是:

data F = +|-|*|... 
data Expr = N|V|MakeExpr F Expr Expr 

有什麼建議嗎?

編輯 -

語法和實現之間的關鍵區別是類型構造器是隱含/在語法中省略。爲什麼Haskell中必須使用類型構造函數?

+1

這不是僞碼 - 它只是一個語法。另外,我不確定你的意思是由'MakeExpr:F - > Expr - > Expr - >(Expr,Expr); MakeExpr f x y =(f,x,y)' - 'MakeExpr'已經在'data Expr = N | V | MakeExpr F Expr Expr'中定義。另外,您可能想要在「N」和「V」變體中記錄實際值。無論如何,我不確定你在問什麼。 – Alec

+0

修正後,現在應該更有意義了。 – dumb0

+0

構造函數不能以'+'等符號開頭。考慮數據F = Plus |減| | DotDotDot'。 –

回答

2

語法和實現之間的關鍵區別是類型構造器是隱含/在語法中省略。爲什麼Haskell中必須使用類型構造函數?

在類型級別有缺陷的語法?是否有意義?所有的條款看起來像他們會檢查類型(允許0,1,...既是Expr也是N子類型,並且x,y,...既是Expr也是V子類型

原因數據構造是強制性的Haskell是專門,以確保您不能有X,Y,......既Expr的和V亞型。

所以你的語法看起來像如何合理的模型你希望你的語言條款能夠正常工作,但作爲一個直接設計你沒有任何意義來表達你的語言術語作爲Haskell數據類型。

基本上,哈斯克爾故意沒有亞型。它確保當您創建新類型(使用newtypedata)時,新類型的所有值都與所有其他現有類型(以及將來創建的所有類型)的值不同。它通過讓用戶定義類型的值始終出現在構造函數中(並且使其不可能「重用」構造函數;每當創建新類型時都會創建新的構造函數)來實現這一點。

Haskell的類型系統的工作方式依賴於這種缺乏亞型的。你可以設計一種允許子類型的語言(也許參見Scala)。但它從根本上不會是Haskell。

但你可以做什麼,而不是定義是這樣的:

data Expr 
    = ExprN N 
    | ExprV V 
    | ExprF Expr Expr 

你仍然不能有一個N價值,只是把它作爲一個Expr。但你可以申請ExprN,然後你有一個Expr。而且,如果Haskell允許您使用N類型的n作爲Expr,但它只是要求您添加一個類型註釋,澄清這就是您的意思;你只需要說ExprN n而不是n :: Expr

同樣,當你有一個Expr,並要在N將其應用功能,case語句中提取從ExprN構造的N(如果它的存在)是不是真的任何比你有更多的代碼寫來檢查你的Expr是否實際上是N


類型構造函數」是在Haskell一個特定術語,這是不是我們在這裏討論的。我非常確定你的意思是「一種類型的構造函數」,但是如果你是偶爾使用這個術語來引用另一個東西的話,你會覺得很迂腐。

把它清除掉,如果你聲明一個類像data Maybe a = Nothing | Just aNothingJust是新數據構造(其對「構造」極有可能意味着一個數據構造函數)和Maybe是一個新的類型構造