求助:实现Prolog二进制计数器,统计连续二进制数序列
Prolog二进制连续序列统计实现
首先纠正你代码里的几个问题:
- 比较列表头部与尾部头部时,需要先提取尾部的头部:对于
[H|T],可以用T = [TH|TT]获取尾部的第一个元素TH,再比较H和TH是否相等。 - 你的代码存在语法错误(比如括号不匹配、未完成的语句),且谓词命名容易和内置类型混淆。
以下是符合需求的实现,支持无限长输入列表:
% 主谓词:输入二进制列表,输出连续序列统计结果 run_length_encoded([H|T], [H, Len|Rest]) :- count_consecutive(H, [H|T], Len, Remaining), run_length_encoded_rest(Remaining, Rest). % 处理剩余列表的辅助谓词 run_length_encoded_rest([], []). run_length_encoded_rest([H|T], [Len|Rest]) :- count_consecutive(H, [H|T], Len, Remaining), run_length_encoded_rest(Remaining, Rest). % 统计连续相同元素的个数,并返回剩余列表 count_consecutive(X, List, Count, Rest) :- count_consecutive_helper(X, List, 0, Count, Rest). % 计数辅助谓词(尾递归,优化内存使用) count_consecutive_helper(_, [], Acc, Acc, []). count_consecutive_helper(X, [X|T], Acc, Count, Rest) :- NewAcc is Acc + 1, count_consecutive_helper(X, T, NewAcc, Count, Rest). count_consecutive_helper(X, [Y|T], Acc, Acc, [Y|T]) :- X \= Y.
代码说明
主谓词
run_length_encoded/2:- 针对非空输入列表,先提取第一个元素作为输出的起始值。
- 调用
count_consecutive/4统计该起始值的连续出现次数,同时得到剩余未处理的列表。 - 调用
run_length_encoded_rest/2处理剩余列表,生成后续的统计结果。
count_consecutive/4与count_consecutive_helper/5:- 用尾递归的方式累加连续相同元素的个数,避免栈溢出,同时返回剩余的列表(即第一个不同元素开始的子列表)。
- 遇到不同元素时,立即停止计数,返回当前累加的结果和剩余列表。
run_length_encoded_rest/2:- 递归处理剩余列表,每次统计下一段连续元素的长度并添加到输出中,直到列表为空。
测试示例
% 测试用户提供的案例 ?- run_length_encoded([0,0,0,1,1,0,0,0,1,1,1,1], Output). Output = [0, 3, 2, 3, 4]. % 测试无限列表(可逐步生成结果) ?- infinite_sequence(Seq), run_length_encoded(Seq, Output). Output = [0, 3, 2, 3, 4, 3, 2|...]. % 生成无限重复的00011序列的辅助谓词 infinite_sequence(S) :- repeat, append([0,0,0,1,1], S, S).
内容的提问来源于stack exchange,提问作者Luc4s_mp
相关产品推荐
相关产品推荐

