2013-03-18 49 views
2

我正在尋找一種方法來使用Scheme中的模式進行搜索。就像,如果我有一個搜索模式Scheme中的綁定變量不知道您有多少個變量

'((x likes y) (y is a hard sport) (x is rich)) 

和輸入

'((Mike likes rugby) (Rachel likes tennis) 
    (rugby is a hard sport) (tennis is easy) 
    (Mike is rich) (Rachel is rich)) 

我應該只得到邁克他有資格獲得每一個限制,唯一的一個。

我一直在試圖做幾個小時。我一直試圖首先將x綁定到Mike,然後在任何地方使用Mike而不是x。問題是,我不知道我有多少變數,有沒有辦法做到這一點,或者我的想法是完全錯誤的?

+0

你有一個你想要完成的實際例子嗎?目前有點模糊 – jozefg 2013-03-18 17:44:05

+0

當然,對不起。我想定義一個函數,它會在我會給它的模式之後進行搜索。假設我有'搜索'和'((Mike喜歡橄欖球)'(Rachel喜歡網球)'((x喜歡y)(y是一項艱苦的運動)(x很豐富))(橄欖球是一項艱難的運動) (網球很容易) (麥克富有)(雷切爾很豐富))作爲'數據'。我想使(模式匹配搜索數據)返回Mike(在這種情況下) – Georgianaevil 2013-03-18 17:47:56

+0

您將不得不提供一些標識確切變量的東西。否則,不清楚說「橄欖球」不是一個變量。 (對我們來說肯定,但更少的方案) – jozefg 2013-03-18 17:50:48

回答

2

你在這裏試圖做的是相當經典的logic programming。我一直用於Scheme的方法是amb運算符上的一些變體。

amb是這樣工作的:

(let ((x (amb 1 2 3 4)) 
     (y (amb 5 6 7 8)) 
    (rule (= 10 (+ x y)) 
    (list x y)) 

,這將使得它們的總和10.現在用這個和其他一些巫術,我們可以使您的系統恢復一些x y

首先,模式將成爲我們的「規則」。所以我們可以說,我們格式化我們的模式是這樣的:

'((list-of-vars) (rule 1) (rule 2) (rule 3)) 

現在對於我們的輸入數據,比方說,它的結構是這樣的:

'((list-of-values) (fact 1) (fact 2) (fact 3)) 

現在我們的生活變得很簡單,我們只是希望有我們的架構宏/程序/巫術做這樣的事情:

(define-syntax resolve 
    (syntax-rules() 
    [(_ ((v1 vs ...) 
     r1 rs ...) 
     ((ps ...) 
    f1 fs ...)) 
    (let* ((v1 (amb ps ...)) 
      (vs (amb ps ...)) 
      ... 
      (sym-table (list (cons (quote v1) v1) 
          (cons (quote vs) vs) 
         ...)) 
      (facts '(f1 fs ...)) 
      (rules '(r1 rs ...))) 
     (map rule (map 
        (lambda (rule) 
        (member (substitute rule sym-table) 
          facts)) 
        rules)) 
     sym-table)])) 

full code in a gist

希望這給你一個出發點,讓我知道你有什麼問題。

+0

首先,謝謝:D。現在,如果我正確地理解了你,你使用let,所以你需要知道有多少變量你有。這是我最大的問題。在我的例子中,我有x和y,但是我可以有n個變量,那麼呢?有沒有辦法「擴展」let塊?先綁定x,然後y,然後z .....等等,否則我註定要失敗? – Georgianaevil 2013-03-18 18:09:09

+0

這就是宏是什麼,即時通訊不是在開玩笑,你實際上可以讓它像這樣擴大。我只是砍掉類似的東西給你看 – jozefg 2013-03-18 19:46:02

+0

Theres一些工作代碼 – jozefg 2013-03-18 20:22:43

4

如果您需要未知數量的變量,請使用association listhash table來存儲名稱 - 值綁定,Scheme提供了處理這兩種數據結構的內置過程。

問題描述和所需匹配的類型看起來很像Prolog或類似logic programming系統的工作。如果您使用Scheme卡住,請考慮實施unification算法(如SICP中所示),或者使用Scheme中嵌入的邏輯編程系統,例如KANRENminiKANREN。而我們在這時,你也應該檢查The Reasoned Schemer作爲參考。