Split Number in its digits, grouped in all possble ways
我有一个数字,假设是 123,我想生成一组所有可能的拆分方式:
1 | [[1, 23], [12, 3], [1, 2, 3]]. |
我想过创建 [1,2,3] 的幂集:
1 2 | ?- findall(Powerset, powerset([1,2,3], Powerset), Z). Z = [[1], [1, 2], [1, 2, 3], [2], [2, 3], [3]]. |
然后将集合组合在一起并用
1 2 3 | [[1], [2, 3]] -> [1, 23] [[1, 2], [3]] -> [12, 3] [[1], [2], [3]] -> [1, 2, 3] |
您是否想到了另一种更简单(更优雅)的解决方案?
我使用来自 gnu Prolog powerset 修改的这个谓词
1 2 3 4 | powerset(L, [H|T]):- append([H|T], _, L). powerset([_|L], P):- powerset(L, P). |
我们可以有一个更集中的谓词来代替 powerset
1 2 3 4 5 | parts(C, [C]). parts(L, Ps) :- append(H, T, L), H \\= [], T \\= [], parts(T, Ts), append([H], Ts, Ps). |
现在
1 2 3 4 5 | ?- number_codes(123,Cs),parts(Cs,Ps),maplist(number_codes,Ns,Ps). Cs = [49, 50, 51], Ps = [[49, 50, 51]], Ns = [123] ; ...etc... |
所以我们可以用 findall
收集有趣的 Ns
1 2 | ?- findall(Ns,(number_codes(123,Cs),parts(Cs,Ps),maplist(number_codes,Ns,Ps)),Rs). Rs = [[123], [1, 23], [1, 2, 3], [12, 3]]. |
这里不需要使用
1 2 3 4 5 6 7 8 9 10 11 12 13 14 |
示例使用:
1 2 3 4 5 | ?- phrase(int_split(123),Zss). Zss = [[1,2,3], [12,3], [1,23], [123]]. ?- phrase(int_split(1234),Zss). Zss = [[1,2,3,4], [12,3,4], [1,23,4], [123,4], [1,2,34], [12,34], [1,234], [1234]]. |