列表的头部是否可以代表多个值

时间:2016-10-15 23:12:27

标签: haskell recursion

如果我调用函数<script> $(document).ready(function() { $("#AA").on("click", function() { $( "#result" ).load( "modals/modaltest.html #modal" ); }); // Adds the modal in orginal project $( ".close" ).click(function() { $("#modal").addClass("md-effect"); setTimeout(function() { $("#modal").remove(); }, 1000); }); // This is the part that doesn't work with the appended html. On button click it is supposed to add a class for animation of modal and then remove html it $(document).mouseup(function(e) { var $modal = $("#modal-content"); // if the target of the click isn't the container... nor a descendant of the container if ($modal.is(e.target) || $modal.has(e.target).length !== 0) return; $('#modal').addClass('md-effect'); setTimeout(function() { $modal.remove(); }, 2000); }); }); </script> (在下面定义 - 它是在列表的每个位置插入数字(或任何类型)的函数),这样生成的列表都是相同的长度< / p>

interleave

但是,我预计列表长度会越来越短,因为对interleave 1 [2,3,4] [[1,2,3,4],[2,1,3,4],[2,3,1,4],[2,3,4,1]] 的递归调用会将列表减去头部(即只有interleave)。由于列表的尾部随着每次调用而变短,我希望结果列表更短。

ys

如果递归调用的list参数越来越短,那么列表的长度如何相同?

我能想象的唯一答案是映射值interleave :: a -> [a] -> [[a]] interleave x [] = [[x]] interleave x (y:ys) = (x:y:ys) : map (y:) (interleave x ys) 代表递归调用中的多个数字(即它是[2,1,3,4]中的2和{ {2,3,1,4]中的{1}}和[2,3,4,1]中的map (y:)但是我不确定这是否可行而且我不知道&#2,3} #39;知道如何在haskell执行期间记录值。

问题,换句话说,2,3(列表的头部)在递归调用中代表多个值?

在回答问题时(如果相关),请确认/解释2,3,4中的y是否只代表一个列表(即它是[1,2,3] ,4-在第一个位置插入整数参数)。

(如果您可以显示func的执行顺序,或者值如何存储在堆栈中,这可能会有所帮助)

1 个答案:

答案 0 :(得分:4)

递归调用的列表长度确实逐渐缩短;但是,该函数修改递归调用的结果以延长它们。让我们从底层建立起来。对于空列表,没有任何有趣的事情发生:

interleave 1 []
= { first clause of definition }
[[1]]

但是当我们到达包含一个元素的列表时,我们已经看到了有趣的事情发生了。具体来说,由于递归调用的结果传递给map (y:),递归调用产生的短列表每个都会扩展一个元素。

interleave 1 [4]
= { list syntax }
interleave 1 (4:[])
= { second clause of definition }
(1:4:[]) : map (4:) (interleave 1 [])
= { recursive call, which produces short answers }
(1:4:[]) : map (4:) [[1]]
= { definition of map, which lengthens each answer }
(1:4:[]) : [4:[1]]
= { list syntax }
[[1,4],[4,1]]

以类似的方式,interleave 1 [3,4]使递归调用interleave 1 [4]生成[[1,4],[4,1]],然后使用map (3:)将其中的每个元素延长为[[3,1,4],[3,4,1]]

现在依次解决您的直接问题:

  

如果递归调用的list参数越来越短,那么列表的长度如何相同?

每次对较短列表进行递归调用时,递归调用的结果会变得更长 - 这些都是完全平衡的,因此调用interleave长度为n列表将会导致长度集合 - n+1列表。

  

can y(列表的头部)在递归调用中表示多个值?

不,列表的头部始终是单个值。真正的魔力是每个递归调用都会添加到头部 - 所以你可以通过许多递归调用获得许多额外的头部。

  

确认/解释(x:y:ys)中的(x:y:ys) : map (y:) (interleave x ys)是否只代表一个列表(即[1,2,3,4-是否在第一个位置插入了整数参数。)

正确。