我必须使用LISP或PROLOG删除列表中元素的外观。
这是一些例子。
输入:'(5 2(3 5(3)5(4 2(2 4)))5 2)
输出:'(5 2(3()5(4(2))))
输出列表的结构保持不变。
感谢您的建议,
答案 0 :(得分:2)
由于这似乎是一项功课,我将仅提供指向解决方案的指针:
顺便说一句,我强烈建议您发布您的工作片段并提出具体问题。像上面这样的普遍问题似乎表明你想要一个解决方案放在你的腿上。
好的,这不是功课。我在智力上引起了人们的兴趣。我解决了。
这是一个递归的步行者。如果您的Lisp执行TCO,它应该可以转换为TCO。
你可以在一个循环中完成它,但这需要维护一个堆栈列表来处理“进入列表”的情况。
我没有声称是惯用的解决方案。
(defparameter input '(5 2 (3 5 (3) 5 (4 2 (2 4))) 5 2))
(defparameter output '(5 2 (3 () 5 (4 (2)))))
(defun remove-every-other-appearence (list &optional (hash-table nil))
(when list ; termination condition
;(format t "~%~a~&" list)
(unless hash-table ; if it's the first time
;(format t "creating hash table~&")
(setf hash-table (make-hash-table))) ; create a hash table
(let ((eut (car list))) ; element under test
;(format t "eut: ~a~&" eut)
(cond
((consp eut) ;Recursion time, it's a list.
;(format t "Recursing~&")
(cons
(remove-every-other-appearence eut hash-table)
(remove-every-other-appearence (cdr list) hash-table)))
(t ;Otherwise...
; Increment seen counter by 1
(setf (gethash eut hash-table 0)
(1+ (gethash eut hash-table 0)))
(cond
((evenp (gethash eut hash-table))
(remove-every-other-appearence (cdr list) hash-table))
;ignore the element
((oddp (gethash eut hash-table))
; if this is the odd occurance
;cons the element back onto the rest of the list
(cons eut (remove-every-other-appearence (cdr list) hash-table)))
(t
(error "This integer is neither even nor odd. We're in trouble"))))))))
* input
(5 2 (3 5 (3) 5 (4 2 (2 4))) 5 2)
* (remove-every-other-appearence input)
(5 2 (3 NIL 5 (4 (2))))
* output
(5 2 (3 NIL 5 (4 (2))))
答案 1 :(得分:0)
FWIW,你的问题陈述还不清楚。
正如我理解这个问题,问题是你有一个任意的“树”,其非叶节点是列表,叶子节点是其他东西。一份“清单清单”。您希望将其视为叶节点的逻辑平面序列,对其进行迭代并删除所有其他叶节点,而不用更改“树”的整体形状,例如唯一改变的是从任何给定节点悬挂的叶子数量。
由此,给出以下输入,您将意识到相应的输出:
input: []
output: []
input: [a,b,c,d]
output: [a,c]
input: [a,[],b,c,d]
output: [a,[],c]
input: [a,[b],c,d]
output: [a,[],c]
input: [a,[b,c,d,e],f,g]
output: [a,[c,e],g]
input: [a,[b,[],[c,d,[e,f,g],h],i],j]
output: [a,[[],[c,[e,g]],i]]
这是一个[未经测试的] prolog解决方案。在其中,我只保留两个状态keep
和remove
,并根据需要在它们之间切换。你得到奇数/偶数免费:它只取决于你启动机器的状态。
应该注意的是,如果传入的数据结构包含任何未绑定/非统一变量,则与获得正确结果不同。不需要的统一会导致问题。需要添加Guard子句以正确处理它们。
% ====================
% The public interface
% ====================
remove_even( Xs , Ys ) :- remove_every_other_node( keep , _ , Xs , [] , Ys ).
remove_odd( Xs , Ys ) :- remove_every_other_node( remove , _ , Xs , [] , Ys ).
%------------------
% The core iterator
%------------------
remove_every_other_node( S , S , [] , T , List ) :-
reverse(T,List)
.
remove_every_other_node( S , N , [X|Xs] , T , List ) :-
process_node( S, S1 , X , T , T1 ) ,
remove_every_other_node( S1 , N , Xs , T1 , List )
.
%----------------------
% The list node handler
%----------------------
process_node( S , S , [] , T , [[]|T] ).
process_node( S , N , [X|Xs] , T , [L1|T] ) :-
remove_every_other_node( S , N , [X|Xs] , [] , L1)
.
process_node( keep , remove , X , T , [X|T] ).
process_node( remove , keep , X , T , T ).
答案 2 :(得分:0)
(defun rea (tree)
(let ((table (make-hash-table)))
(labels ((fn (x)
(unless (and x (atom x) (evenp (incf (gethash x table 0))))
(list (if (atom x) x (mapcan #'fn x))))))
(car (fn tree)))))