2015-09-29 39 views
2

我試圖使用listsclpfd庫生成一個隨機長度列表。我已經試過如下:生成限制之間的所有長度的列表

?- use_module(library(clpfd)). 
?- use_module(library(lists)). 

gen_mem_burst(X) :- 
    Len in 1..2, 
    length(X, Len). 

我看到的Prolog首先發現只有一個列表元素,然後用兩個元素的解決方案,正如我預期的解決方案。之後,它會發出「超出全局堆棧」的信息。我追蹤到它,並且我注意到它一直試圖將Len設置爲3,4,5,等等。我怎樣才能讓它停止?

我是序言新手,我甚至不確定這是否是有效的使用模型。在我使用的其他基於約束的語言(例如SystemVerilog)中,這很容易實現。

回答

2

至少在SWI-Prolog中,當涉及約束變量時,length/2無法完全按預期工作:我卡在exact same problem上。有幾個很好的答案可以給你指針。

無論如何,回答你的問題的標題:生成隨機長度的列表:

?- set_random(seed(1)), /* if you want to seed */ 
    Len is random(9), 
    length(L, Len). 
Len = 2, 
L = [_G2748, _G2751]. 

如果你只需要兩個極限之間產生的所有長度列表,

?- between(1, 3, Len), length(L, Len). 

可能是最簡單的方法。

+1

我想我選擇的標題很差。我的意圖是能夠產生所有可能性(即,長度爲1的列表和長度爲2的列表)。我從鏈接中使用了'fd_length(..)'方法。 –

+0

@Tudor Hm,還不確定。你絕對想爲此使用約束變量嗎?請參閱我的答案的更新,以獲取無需執行的方法。如果你真的不需要在列表長度上放置正確的CLP(FD)約束,那麼'fd_length/2'就好,它是一種矯枉過正。 –

+1

使用'between'對於我的需求來說更酷(因爲我只需要掃描),但應該記住'fd_length/2'方法應該永遠需要爲列表長度添加更復雜的約束。 –