0

I am trying to define a palindrome where the number of a's is one less than the number of b's. I cant seem to figure out how to write it properly

   please-->palindromes.
   palindromes-->[].
   palindromes-->[a].
   palindromes-->[b].
   palindromes--> [b],palindromes,[b].
false
  • 10,264
  • 13
  • 101
  • 209
user1850254
  • 2,091
  • 3
  • 16
  • 17

2 Answers2

0

Think about this: where the surplus 'b' could stay ? In a palindrome, there is only one such place. Then change the symmetric definition, that in BNF (you already know as translate to DCG) would read

S :: P
P :: a P a | b P b | {epsilon}
CapelliC
  • 59,646
  • 5
  • 47
  • 90
0

You're on the right track, you just need a way to deal with the difference in counts. You can do this by adding a numeric argument to your palindromes grammar term.

First I'll define an ordinary Prolog rule implementing "B is two more than A":

plus2(A,B) :- number(A), !, B is A+2.
plus2(A,B) :- number(B), !, A is B-2.
plus2(A,B) :- var(A), var(B), throw(error(instantiation_error,plus2/2)).

Then we'll say palindromes(Diff) means any palindrome on the given alphabet where the number of b letters minus the number of a letters is Diff. For the base cases, you know Diff exactly:

palindromes(0) --> [].
palindromes(-1) --> [a].
palindromes(1) --> [b].

For the recursive grammar rules, we can use a code block in {braces} to check the plus2 predicate:

palindromes(DiffOuter) --> [b], palindromes(DiffInner), [b],
    { plus2(DiffInner, DiffOuter) }.
palindromes(DiffOuter) --> [a], palindromes(DiffInner), [a],
    { plus2(DiffOuter, DiffInner) }.

To finish off, the top-level grammar rule is simply

please --> palindromes(1).
aschepler
  • 70,891
  • 9
  • 107
  • 161