# Keep getting the error "Arguments are not instantiated enough" can't figure out why

Keep getting error `Arguments are not sufficiently instantiated`

for the addition rule multiplication I wrote as shown below.

```
mult(_, 0, 0). %base case for multiplying by 0
mult(X, 1, X). % another base case
mult(X, Y, Z) :-
Y > 1,
Y1 is Y - 1,
mult(X, Y1, Z1),
Z is X + Z1.
```

I am new to Prolog and am really struggling with such simple problems.

Any recommendation for books or online tutorials would be great.

I am running it on SWI-Prolog on Ubuntu Linux.

source to share

~~I think you have removed the last two calls. You don't mean:~~

```
mult(X,Y,Z):- Y>1,Y1 is Y-1, Z1 is X+Z, mult(X,Y1,Z1).
```

Strike> Edit: It doesn't matter if you look at the code again, it doesn't make sense. I believe your original code is correct.

As for the reason behind this error, I need to know how you call the predicate. Can you provide an example of input?

The correct way to call the predicate is `mult(+X, +Y, ?Z)`

:

`?- mult(5,0,X). X = 0 ?- mult(5,1,X). X = 5 ?- mult(5,5,X). X = 25 ?- mult(4,4,16). yes ?- mult(3,3,10). no`

etc .. Calling this function with a free variable in the first two arguments will result in this error, because one of them will be used on the right side `is`

or on both sides of `<`

, and these predicates expect.

source to share

The `mult/3`

first two arguments must be known in your definition . If one of them is still a variable, a creation error will occur. For example. `mult(2, X, 6)`

will result in a creation error, although this `X = 3`

is the correct answer; in fact, the only answer.

There are several options:

successor-arithmetics, constraints, or meta-word predicates.

Here's a starting point with successor arithmetic:

```
add(0,Y,Y).
add(s(X),Y,s(Z)) :- add(X,Y,Z).
```

Another approach would be to use integer constraints. YAP and SWI have `library(clpfd)`

which can be used in a very flexible way: both for regular integer computation and for more general constraints. Of course, the multiplication is already predefined:

? - A * B # = C. A * B # = C. ? - A * B # = C, C = 6. C = 6, A in -6 .. -1 \ /1..6, A * B # = 6, B in -6 .. -1 \ /1..6. ? - A * B # = C, C = 6, A = 2. A = 2, B = 3, C = 6.

Meta-logic predicates: I can not recommend this option, in which you would use `var/1`

, `nonvar/1`

, `ground/1`

, to distinguish between different cases and handle them differently. These are so prone to errors that I have rarely seen the correct program using them. In fact, even very famous textbooks contain serious errors!

source to share