2017-05-30 58 views
1

早上好。 我需要你的帮助。 我想从大小为N的列表中进行列表(矩阵大小SQRT(N)* SQRT(N))的列表从列表中制作矩阵

我试过,但它不为我工作:(

gen(L,T,Matrix) 

其中T是矩阵的大小 你是免费的,如果你想

例如增加更多的PARAM

gen([1,2,3,4,5,6,7,8,9],3,Matrix) 
Matrix = [[1,2,3],[4,5,6],[7,8,9]] 
+1

如果您的列表长度不是一个完美的正方形,您会发生什么?这看起来很简单:列表只是矩阵的行或列主表示。有什么问题? – duffymo

+1

为什么你需要'T'?为什么列表不是从列表的“length/2”派生的。 –

+0

你有什么尝试,你在哪里专门卡住?而且,你想要的矩阵与给出的列表有什么关系? – lurker

回答

2

这实际上是一个相当简单的问题。关键是要记住,append/3有许多实例化模式,并且可以用来不仅仅是胶水名单在一起,但也除了打破他们:

?- append(X, Y, [1,2,3,4]). 
X = [], 
Y = [1, 2, 3, 4] ; 
X = [1], 
Y = [2, 3, 4] ; 
X = [1, 2], 
Y = [3, 4] ; 
X = [1, 2, 3], 
Y = [4] ; 
X = [1, 2, 3, 4], 
Y = [] ; 
false. 

您可以使用length/2控制列表中,您的大小以及:

?- append(X, Y, [1,2,3,4]), length(X, 3). 
X = [1, 2, 3], 
Y = [4] ; 
false. 

这几乎是你需要在这里的一切。剩下的就是用递归调用来包装它。你需要一个基本情况:

gen([], _, []). 

这本质上说,如果我出平表示或矩阵表示我的尺寸并不重要。

现在递归情况:

gen(List, T, [Start|Rest]) :- 
    append(Start, Remainder, List), 
    length(Start, T), 
    gen(Remainder, T, Rest). 

这是一个非常基本的递归谓词。 append/3后跟length/2步骤与上面相同;他们建立List的前缀长度为T作为结果的下一个块。然后,我们递归地将自己应用于剩余的列表以生成结果的其余部分。

作为一个冷静的一面好处,这个谓词是双向的:

?- gen(X, 3, [[1, 2, 3], [4, 5, 6], [7, 8, 9]]). 
X = [1, 2, 3, 4, 5, 6, 7, 8, 9] ; 
false. 

是多漂亮!

+0

和那有多聪明!我非常感谢@Daniel –