这个递归的结果树不是我的东西,这可能证明我不完全理解递归中列表/元组的行为.如果有人可以解释我在这个例子中做错了什么,并解释了正确的思考方式,我会非常感激.
move([],{Main, One, Two}) ->
{Main, One, Two};
move([X|Xr], {Main, One, Two}) ->
[{Main, One, Two}, move(Xr, single(X, {Main, One, Two}))].
Run Code Online (Sandbox Code Playgroud)
期望的结果(一个包含3个元组的列表):
[{[a,b],[],[]}, {[a],[b],[]}, {[],[b],[a]}, {[b],[],[a]}]
Run Code Online (Sandbox Code Playgroud)
实际结果(包含元组和列表的列表,包含元组和列表...):
[{[a,b],[],[]},[{[a],[b],[]},[{[],[b],[a]},[{[b],[],[a]}]]]]
Run Code Online (Sandbox Code Playgroud)
你有两个问题:
|不是,像@nmichaels所提到的那样.move/2返回一个列表,因此终止子句也必须返回一个列表.在您的示例中没有看到这一点,因为第一个问题隐藏了它.因此生成的代码将是:
move([X|Xr], {Main, One, Two}) ->
[{Main, One, Two} | move(Xr, single(X, {Main, One, Two}))];
move([], {Main, One, Two}) ->
[{Main, One, Two}].
Run Code Online (Sandbox Code Playgroud)
我翻了条款的顺序,因为我个人更喜欢用这种方式写它们.在这种情况下没有根本区别.我假设single/2返回一个元组.
您实际上可以通过删除元组的所有知识来优化此代码,move/2因为它从未实际使用内部结构.所以:
move([X|Xr], Tuple) ->
[Tuple | move(Xr, single(X, Tuple))];
move([], Tuple) ->
[Tuple].
Run Code Online (Sandbox Code Playgroud)