2009-12-17 11 views
5

मैं किसी सूची में उदाहरणों की संख्या की गणना कर रहा हूँ ...prolog: फिक्सिंग एकाधिक जवाब (कट का उपयोग कर?)

count(_,[],N,N). 
count(Elem,[Elem|List],N,M) :- !, N1 is N+1, count(Elem,List,N1,M). 
count(Elem,[_|List],N,M) :- count(Elem,List,N,M). 

तो, मैं इस अप prolog में लिखा है दो तरह से है, और पहले एक काम करता है (ऊपर), लेकिन मुझे यह जानने के लिए उत्सुक था कि दूसरा क्यों नहीं करता (या बल्कि, मुझे कई जवाब देगा - केवल पहला ही सही है) यह क्यों है?

बहुत धन्यवाद

count(Z,X,R) :- count2(Z,X,R,0). 
count2(W,[H|T],L,A):- (W == H), Lnew is A+1, count2(W,T,L,Lnew). 
count2(W,[H|T],L,A):- count2(W,T,L,A). 
count2(W,[],A,A). 

उत्तर

0

आपके प्रश्न का उत्तर ... कटौती भी शामिल है। कट हमेशा सफल होता है और व्युत्पन्न वृक्ष "काटने" का दुष्प्रभाव होता है। असल में आप एक कट पास बैकट्रैक नहीं कर सकते हैं।

पहला उदाहरण कटौती निष्पादित करेगा यदि लक्ष्य दूसरे नियम के साथ एकीकृत करता है। एक मायने में, वह विकल्प तय हो जाता है। यदि विफलता या बैकट्रैकिंग हो रही है तो यह कट पर bacjtrack नहीं है इस प्रकार कई उत्तरों को खत्म कर देता है। जब उत्तर पारस्परिक रूप से अनन्य होते हैं तो कट उपयोगी होता है। यही है, जब आपको पहला जवाब मिलता है तो कोई अन्य समझ में नहीं आता है।

+0

मैंने कटौती के साथ दूसरे की कोशिश की, इसलिए: गिनती (जेड, एक्स, आर): - गिन 2 (जेड, एक्स, आर, 0)। गिनती 2 (डब्ल्यू, [एच | टी], एल, ए): -!, (डब्ल्यू == एच), लेन्यू ए + 1, गिन 2 (डब्ल्यू, टी, एल, एलन्यू) है। गिनती 2 (डब्ल्यू, [एच | टी], एल, ए): - गिन 2 (डब्ल्यू, टी, एल, ए)। count2 (डब्ल्यू, [], ए, ए)। लेकिन यह काम करने के लिए प्रतीत नहीं होता है, इसलिए मैंने सोचा कि शायद मूल रूप से कोड किसी भी तरह से त्रुटिपूर्ण है –

-1

समझ गया!

यहाँ एक समाधान है कि काम करता है:

count(Z,X,R) :- count2(Z,X,R,0). 
count2(W,[H|T],L,A):- (W == H), !, Lnew is A+1, count2(W,T,L,Lnew). 
count2(W,[H|T],L,A):- count2(W,T,L,A). 
count2(W,[],A,A). 

धन्यवाद विन्सेंट - तुम मुझे कटौती फिर से मिलना बनाया!

+0

एक समाधान जो काम करता है? नहीं! '(!)/0' का उपयोग करने के हानिकारक प्रभावों का निरीक्षण करें: यह प्रोग्रामर के आत्मविश्वास को बढ़ावा देता है कि कोड सही है, जबकि (साथ ही) कोड को भंगुर/मरम्मत की किसी भी संभावना से परे टूटा हुआ है। – repeat

2

आपका दूसरा प्रयास कई समाधानों का उत्पादन करने का कारण यह है कि दूसरा गिनती 2 खंड डब्ल्यू और एच को समान मान लेने से नहीं रोकता है। तो यदि गिनती 2 का पहला खंड सफल होता है, तो यह दूसरे खंड पर फिर से बैकट्रैक और सफल हो सकता है।

आप विन्सेंट Ramdhanie का कहना है के रूप में एक कट का उपयोग करके इसे ठीक कर सकते हैं, या आप बस, डब्ल्यू और एकीकृत से एच को रोकने के लिए इस तरह के दूसरे खंड में एक स्पष्ट जांच में जोड़ सकते हैं अगर आप एक कटौती के उपयोग से बचने के लिए पसंद करते हैं:

count(Z,X,R) :- count2(Z,X,R,0). 
count2(W,[W|T],L,A):- Lnew is A+1, count2(W,T,L,Lnew). 
count2(W,[H|T],L,A):- W \= H, count2(W,T,L,A). 
count2(_,[],A,A). 

इसके अलावा, ध्यान दें कि पहला गिनती 2 खंड अब अंतर्निहित एकीकरण का उपयोग करता है। एक स्पष्ट जांच के बजाय। यह मेरी राय में पढ़ने के लिए थोड़ा छोटा और आसान है। बेशक एक कारण यह था कि आप एकीकरण के बजाय समानता का उपयोग क्यों कर रहे थे।

संबंधित मुद्दे