[英]Is there a functional programming concept equivalent to the flip-flop operator in Perl or Ruby?
Ruby(和Perl)有一个触发器的概念:
file = File.open("ordinal")
while file.gets
print if ($_ =~ /third/) .. ($_ =~ /fifth/)
end
给出了一系列序数,例如
first
second
third
fourth
fifth
sixth
当它达到“第三”时开始打印,当达到“第五”时停止打印:
third
fourth
fifth
是否有一个函数式编程的概念类似于此,或将这种通常的术语来描述takewhile
S' 我不是在问一个特定的语言,而是用你用来形容它的术语。
在诸如haskell之类的函数式语言中,您可以将翻转和翻转条件作为谓词传递,并根据它过滤输入列表。 例如,以下是haskell中flipflop
的定义(如果你不知道haskell,请不要担心实现 - 关键部分是如何使用它):
flipflop flip flop =
uncurry (++) . second (take 1) . break flop . dropWhile (not . flip)
这是它的使用方法:
> flipflop (== 3) (== 5) [1..10]
[3,4,5]
这是通过使用更高阶函数来制作有效的新语言构造的一个例子。
我不知道在功能语言中是否有该特殊名称。
取决于功能语言。 这个怎么样?
ff_gen =
lambda{ |first, *conditions|
flipflop = false
condition = first
lambda{ |v|
if condition && condition[v]
condition = conditions.shift
flipflop = !flipflop
true
else
flipflop
end
}
}
ff = ff_gen[lambda{|v| v == 3}, lambda{|v| v == 5}, lambda{|v| v == 7}, lambda{|v| v == 11}]
puts (0..20).select{ |i| ff[i] }.inspect # => [3, 4, 5, 7, 8, 9, 10, 11]
补充:当然,Ruby不是纯函数式语言,所以我决定在Erlang中重写它:
#!/usr/bin/env escript
flipflop(E, {[H|T] = Conditions, FlipFlop}) ->
case H(E) of
true ->
{true, {T, not FlipFlop}};
false ->
{FlipFlop, {Conditions, FlipFlop}}
end;
flipflop(_, {[], FlipFlop}) ->
{FlipFlop, {[], FlipFlop}}.
flipflop_init(Conditions) ->
{[], {Conditions, false}}.
main([]) ->
{L, _} =
lists:foldl(
fun(E, {L2, FFState}) ->
case flipflop(E, FFState) of
{true, FFState2} ->
{[E|L2], FFState2};
{false, FFState2} ->
{L2, FFState2}
end
end,
flipflop_init([
fun(E) -> E == 3 end,
fun(E) -> E == 5 end,
fun(E) -> E == 7 end,
fun(E) -> E == 11 end
]),
lists:seq(0,20)
),
io:format("~p~n", [lists:reverse(L)]),
ok.
注意:事实上,经典的触发器应该像dropwhile(!first) - > takewhile(!second)一样工作,因此Ruby的触发器是ad hoc触发器(与电子器件中的触发器相比)。
与@ nanothief的解决方案相同,但在Scala中:
def flipFlop[A](flip: A => Boolean, flop: A => Boolean, seq: Seq[A]): Seq[A] = {
val (p, q) = seq.dropWhile(!flip(_)).span(!flop(_))
p ++ q.take(1)
}
样品运行:
> flipFlop[Int](_ == 3, _ == 5, Nil)
List()
> flipFlop[Int](_ == 3, _ == 5, 1 to 19)
Vector(3, 4, 5)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.