【问题标题】:Can "if" be implemented using "call/cc"?可以使用“call/cc”实现“if”吗?
【发布时间】:2011-07-29 03:27:46
【问题描述】:

有人告诉我“call/cc”可用于实现任意控制流构造,因此我尝试使用“call/cc”来实现所有此类构造,但我遇到了麻烦。假设我没有“if”,我将如何使用“define-syntax”和“call/cc”来实现它?有可能还是我被误导了?我知道如何使用“call/cc”实现无条件跳转,但在机器级别,条件执行是使用分支指令执行的,分支指令的执行取决于处理器的状态位。如果没有这种类型的构造,我看不到它是如何完成的。

【问题讨论】:

    标签: functional-programming scheme control-flow callcc define-syntax


    【解决方案1】:

    你不能——你必须有某种方法来测试事物并根据它们的真假采取行动。不过,您可以通过布尔值的一些功能表示来接近。例如,使用常见的教堂编码:

    (define (true x y) x)
    (define (false x y) y)
    

    现在您可以将测试(返回这些编码布尔值之一)视为接受“成功”延续和“失败”延续的函数,并使用它来继续:

    (define (if c x y) (c x y))
    

    如果你想对此进行实验,你需要考虑到 Scheme 不是一种惰性语言这一事实​​,所以你需要把事情做好。例如:

    (define (true x y) (x))
    (define (false x y) (y))
    (define-syntax if
      [(if c x y) (c (lambda () x) (lambda () y))])
    

    (但您仍然需要修改现有谓词等以返回这些布尔值。)

    不管怎样,call/cc 本身并没有真正做任何相关的事情......

    【讨论】:

    • 我不认为你可以。将布尔值定义为函数会改变语言的语义,因此必须重新定义布尔运算符,因为在 Scheme 中,任何函数在被视为布尔值时都是非假的。
    • 是的,这样的改变会导致不同的语言......这就是为什么我从“你不能”开始。
    【解决方案2】:

    您可以仅使用高阶过程来实现 if。这是明显的 uncurried Church 编码:

    IF ? T E === (? (lambda () T) (lambda () F))
    
    TRUE     === (lambda (t _) (t))
    FALSE    === (lambda (_ f) (f))
    

    您根本不需要延续。 True 是执行第一个参数的二进制函数; False 是执行它的第二个参数的二进制函数。 If 是一个三元函数,通过获取由测试 (?) 确定的 True/False 并将它们排序在一起,并给它两个延迟结果的函数。

    【讨论】:

      猜你喜欢
      • 2012-04-12
      • 2010-12-15
      • 1970-01-01
      • 2014-09-02
      • 2015-04-13
      • 2018-01-27
      • 2016-03-21
      • 2019-12-14
      • 2019-12-13
      相关资源
      最近更新 更多