交换逻辑运算符参数以加快评估速度?
Swap logical operator arguments for faster evaluation?
是否有任何编程语言实现逻辑运算(例如 AND、OR)参数的交换以加快计算速度?
示例(我认为这种方法可以用像 Haskell 这样的惰性求值语言来实现)
- 假设我们定义了两个谓词
A
和B
。
- 在程序执行期间,
B
被计算为 "True" 而 A
未被计算
- 在后面的执行中我们有条件
IF A OR B
- 交换"OR"的参数,条件变为
IF B OR A
- 条件被评估为 "True" 而没有评估
A
在惰性求值下,AND 和 OR 不可交换。
foo :: Int -> Bool
foo n = False && foo (n+1) -- evaluates to False
bar :: Int -> Bool
bar n = bar (n+1) && False -- diverges
在热切求值(严格语义)和无副作用的情况下,它们是可交换的。不过,我不知道某些编译器在这里进行了任何常规优化。 (常量折叠到一边。)
如果存在副作用,AND/OR 当然是不可交换的。例如,Ocaml 编译器不能交换参数,除非它能证明至少其中一个参数没有副作用。
它不会作为语言的一部分自动完成(可能是因为执行此重新排序检查不是 免费,因此您通常最终会为优化付费'被制造)。但是,您可以为此使用一些库函数。参见,例如,unamb
。有了它,你可以写
(|||) :: Bool -> Bool -> Bool
a ||| b = (a || b) `unamb` (b || a)
如果一种操作的计算成本更低,则可以选择它。
是否有任何编程语言实现逻辑运算(例如 AND、OR)参数的交换以加快计算速度?
示例(我认为这种方法可以用像 Haskell 这样的惰性求值语言来实现)
- 假设我们定义了两个谓词
A
和B
。 - 在程序执行期间,
B
被计算为 "True" 而A
未被计算 - 在后面的执行中我们有条件
IF A OR B
- 交换"OR"的参数,条件变为
IF B OR A
- 条件被评估为 "True" 而没有评估
A
在惰性求值下,AND 和 OR 不可交换。
foo :: Int -> Bool
foo n = False && foo (n+1) -- evaluates to False
bar :: Int -> Bool
bar n = bar (n+1) && False -- diverges
在热切求值(严格语义)和无副作用的情况下,它们是可交换的。不过,我不知道某些编译器在这里进行了任何常规优化。 (常量折叠到一边。)
如果存在副作用,AND/OR 当然是不可交换的。例如,Ocaml 编译器不能交换参数,除非它能证明至少其中一个参数没有副作用。
它不会作为语言的一部分自动完成(可能是因为执行此重新排序检查不是 免费,因此您通常最终会为优化付费'被制造)。但是,您可以为此使用一些库函数。参见,例如,unamb
。有了它,你可以写
(|||) :: Bool -> Bool -> Bool
a ||| b = (a || b) `unamb` (b || a)
如果一种操作的计算成本更低,则可以选择它。