Bạn có thể yêu cầu đầu ra của desugarer của GHC, tuy nhiên điều này cũng sẽ desugar rất nhiều cú pháp khác.
Thứ nhất, chúng tôi sẽ đặt mã của bạn trong một module Foo.hs
:
module Foo where
a = do x <- [3..4]
[1..2]
return (x, 42)
Tiếp theo, chúng tôi sẽ hỏi GHC để biên dịch nó và đầu ra là kết quả sau khi giai đoạn desugaring:
$ ghc -c Foo.hs -ddump-ds
Đầu ra có thể trông khá lộn xộn, bởi vì nó là một biến thể của Haskell được gọi là Core được sử dụng làm ngôn ngữ trung gian của GHC. Tuy nhiên, nó không quá khó đọc khi bạn quen với nó. Ở giữa một số định nghĩa khác mà chúng tôi tìm thấy bạn:
Foo.a :: [(GHC.Integer.Type.Integer, GHC.Integer.Type.Integer)]
LclIdX
[]
Foo.a =
>>=_agg
@ GHC.Integer.Type.Integer
@ (GHC.Integer.Type.Integer, GHC.Integer.Type.Integer)
(enumFromTo_ag7
(GHC.Integer.smallInteger 3) (GHC.Integer.smallInteger 4))
(\ (x_adf :: GHC.Integer.Type.Integer) ->
>>_agn
@ GHC.Integer.Type.Integer
@ (GHC.Integer.Type.Integer, GHC.Integer.Type.Integer)
(enumFromTo_ags
(GHC.Integer.smallInteger 1) (GHC.Integer.smallInteger 2))
(return_aki
@ (GHC.Integer.Type.Integer, GHC.Integer.Type.Integer)
(x_adf, GHC.Integer.smallInteger 42)))
Core là không quá xinh đẹp, nhưng có thể đọc nó là rất hữu ích khi làm việc với GHC, như bạn có thể đọc các bãi sau giai đoạn sau để xem cách GHC tối ưu hóa mã của bạn.
Nếu chúng ta loại bỏ các _xyz
hậu tố bổ sung bởi các đổi tên, cũng như các ứng dụng loại @ Xyz
và các cuộc gọi đến GHC.Integer.smallInteger
, và làm cho các nhà khai thác ghi vào một lần nữa, bạn lại với một cái gì đó như thế này:
Foo.a :: [(GHC.Integer.Type.Integer, GHC.Integer.Type.Integer)]
Foo.a = enumFromTo 3 4 >>= \x -> enumFromTo 1 2 >> return (x, 42)
thực sự 'm >> = (\ _ -> k)' là 'm >> k' –
Lambdabot có một plugin" hoàn tác "mà desugars làm ký hiệu –
Tôi chỉ học và cảm thấy như thế này là chìa khóa để thực sự hiểu chi tiết của một trường hợp cụ thể - tất cả chúng đều được viết dưới dạng >> = –