在模式中重用列表

发布于 2024-10-20 16:33:02 字数 135 浏览 2 评论 0原文

当我写:

sort [x] = [x]

编译器是否足够聪明以重用相同的列表,或者我是否必须明确说明它?

sort xs@[_] = xs

When I write:

sort [x] = [x]

Is the compiler smart enough to reuse the same list, or do I have to be explicit about it?

sort xs@[_] = xs

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

朮生 2024-10-27 16:33:02

它足够聪明吗?让我们来看看!

ezyang@javelin:~$ cat Foo.hs
module Foo where
foo [x] = [x]

这是 STG:

ezyang@javelin:~$ ghc --make Foo.hs -ddump-stg -fforce-recomp
[1 of 1] Compiling Foo              ( Foo.hs, Foo.o )

==================== STG syntax: ====================
Foo.foo =
    \r srt:(0,*bitmap*) [ds_sdP]
        let-no-escape {
          fail_sdO =
              sat-only \r srt:(0,*bitmap*) [ds1_sdN]
                  Control.Exception.Base.patError "Foo.hs:2:0-12|function foo";
        } in 
          case ds_sdP of wild_sdY {
            [] -> fail_sdO GHC.Prim.realWorld#;
            : x_sdV ds1_sdT ->
                case ds1_sdT of wild1_sdZ {
                  [] -> : [x_sdV GHC.Types.[]];
                  : ipv_se0 ipv1_se1 -> fail_sdO GHC.Prim.realWorld#;
                };
          };
SRT(Foo.foo): [Control.Exception.Base.patError]

有趣的是这一行:

                  [] -> : [x_sdV GHC.Types.[]];

我们看到我们正在为 x_sdV[] 创建一个新的 cons-cell。所以,不。不过,这还不算太糟糕,因为 x_sdV 本身是共享的,所以它只是一个构造函数;此外,我们正在强制列表的主干xs,因此GHC无论如何都需要重写它。所以不用担心。

Is it smart enough? Let's see!

ezyang@javelin:~$ cat Foo.hs
module Foo where
foo [x] = [x]

Here is the STG:

ezyang@javelin:~$ ghc --make Foo.hs -ddump-stg -fforce-recomp
[1 of 1] Compiling Foo              ( Foo.hs, Foo.o )

==================== STG syntax: ====================
Foo.foo =
    \r srt:(0,*bitmap*) [ds_sdP]
        let-no-escape {
          fail_sdO =
              sat-only \r srt:(0,*bitmap*) [ds1_sdN]
                  Control.Exception.Base.patError "Foo.hs:2:0-12|function foo";
        } in 
          case ds_sdP of wild_sdY {
            [] -> fail_sdO GHC.Prim.realWorld#;
            : x_sdV ds1_sdT ->
                case ds1_sdT of wild1_sdZ {
                  [] -> : [x_sdV GHC.Types.[]];
                  : ipv_se0 ipv1_se1 -> fail_sdO GHC.Prim.realWorld#;
                };
          };
SRT(Foo.foo): [Control.Exception.Base.patError]

The interesting bit is this line:

                  [] -> : [x_sdV GHC.Types.[]];

where we see that we are creating a new cons-cell for x_sdV and []. So, no. However, this is not too bad, because x_sdV itself is shared, so it’s only a single constructor; furthermore, we are forcing the spine of the list xs, so GHC would need to rewrite it anyway. So don't worry about it.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文