Pyret 編程語言:探索腳本語言和函數式編程的融合
Pyret 是一門基于 JavaScript 的腳本語言,旨在成為編程教育的絕佳選擇,同時探索腳本語言和函數式編程的融合。目前 Pyret 正處于積極設計和開發階段,開發者可以自由使用或對其進行修改。
Pyret 語法介紹
Pyret 具有受 Python 啟發的函數、列表和運算符語法,其迭代結構 (Iteration constructs) 的設計為了調用其他語言中的迭代結構。
- fun to-celsius(f):
- (f - 32) * (5 / 9)
- end
- for each(str from [list: "Ahoy", "world!"]):
- print(str)
- end
Pyret 支持簡潔、富有表現力、遞歸的數據聲明,支持可選的類型注釋,支持增量添加,以滿足各種教學風格和課程需求。
- data BinTree:
- | leaf
- | node(value, left :: BinTree, right :: BinTree)
- end
Pyret 的測試是編程過程的自然組成部分。函數可以在where:子句中結束,該子句為函數提供了單元測試,并且這些斷言 (Assertions) 會被動態檢查。
- fun sum(l):
- cases (List) l:
- | empty => 0
- | link(first, rest) => first + sum(rest)
- end
- where:
- sum([list: ]) is 0
- sum([list: 1, 2, 3]) is 6
- end
對于縮進的問題,Pyret 團隊認為縮進對于代碼的可讀性至關重要,但他們不希望通過程序的空格來確定其含義。相反,程序的含義應該決定它的縮進結構。縮進只是另一個上下文敏感的規則。
明確的語法(Pyret 使用顯式end分隔符的原因)意味著開發者可以從電子郵件或 Web 復制和粘貼代碼,而不會改變其含義。IDE 會幫助開發者重新縮進代碼,無需擔心這樣做會改變程序的含義。
亮點
注解 (Annotations)
與大多數腳本編程語言不一樣,Pyret 支持開箱即用地檢查參數上的注解。
Python
- def square(n : int) -> int:
- return n * n
- square("5")
- # Error at multiplication:
- # Can't multiply sequence by
- # non-int of type 'str'
Pyret
- fun square(n :: Number) -> Number:
- n * n
- end
- square("5")
- # With type checker off:
- # The Number annotation was not
- # satisfied by the value "5"
- # With type checker on:
- # Number is incompatible with String
支持長度較長的數字類型
Java
- // this is not true
- ((1 / 3) * 3) == 1
Pyret
- # this is true
- ((1 / 3) * 3) == 1
結構化數據
Pyret 為編寫數據定義提供了優雅的機制,而無需開發者具備對類的認知背景,以及語法開銷。
Python
- class BinTree:
- pass
- class leaf(BinTree):
- def __init__(self):
- pass
- class node(BinTree):
- def __init__(self, v, l, r):
- self.v = v
- self.l = l
- self.r = r
Pyret
- data BinTree:
- | leaf
- | node(v, l, r)
- end
Pyret 在使用結構化數據方面也非常靈活,并在其底層公開了一個簡單的對象模式,支持結構化代碼與更多 nominal 模式搭配使用。
OCaml
- type animal =
- | Elephant of string * float
- | Tiger of string * float
- | Horse of string * int
- ...
- let name_of_animal a =
- match a with
- | Elephant(name, _)
- | Tiger(name, _)
- | Horse(name, _) -> name
- ...
Pyret
- data Animal:
- | elephant(name, weight)
- | tiger(name, stripes)
- | horse(name, races-won)
- ...
- end
- fun animal-name(a :: Animal):
- a.name
- end
Racket
- (struct elephant (name weight))
- (struct tiger (name stripes))
- (struct horse (name races-won))
- ...
- (define (animal-name a)
- (cond
- [(elephant? a) (elephant-name a)]
- [(tiger? a) (tiger-name a)]
- [(horse? a) (horse-name a)]
- ...))
Pyret
- data Animal:
- | elephant(name, weight)
- | tiger(name, stripes)
- | horse(name, races-won)
- ...
- end
- fun animal-name(a :: Animal):
- a.name
- end
運行 Pyret
通過訪問 code.pyret.org 直接在瀏覽器中運行 Pyret,這是最簡單的入門方法。查看導覽以了解小部分程序和語法示例。
如果希望在命令行中在使用 Pyret 進行編程,需要從 https://www.npmjs.com/package/pyret-npm 安裝pyret-npm,安裝命令如下:
- npm install -g pyret-npm
根據 Pyret 的官網介紹,目前該項目正在積極開發三個非常重要的功能:
- 支持靜態類型,提供帶有標簽聯合 (tagged unions) 和類型檢查器的傳統類型系統
- 使用表作為存儲現實世界數據的關鍵類型
- 交互式計算模型基于 “world” model
其團隊認為 Pyret 也已經足夠成熟,因為它實現了自托管編譯器。這意味著,當開發者在瀏覽器中運行 Pyret 時,它會加載實現了 Pyret-to-JavaScript 編譯器的 JavaScript 代碼(即開發者輸入的 Pyret 代碼會編譯成 JavaScript 并在瀏覽器中運行)。這個編譯器是由 Pyret-to-JavaScript 編譯器通過編譯 Pyret-to-JavaScript 編譯器產生的。
本文轉自OSCHINA
本文標題:Pyret 編程語言:探索腳本語言和函數式編程的融合
本文地址:https://www.oschina.net/news/156822/pyret-language