I have to compute a polynomial like this --
f(x) = x^4 - 2.274x^3 + 1.8x^2 - 0.576x + 1.0
with this lisp function --
(defun polynomial (x)
(+ (+ (+ (+ (expt x 4) (* -2.274 * (expt x 3)))
(* 1.8 (* x x))) (* -0.576 x)) 0.1))
when I call (polynomial 0.5) the result is different at different evaluations, like this --
CL-USER> (polynomial 0.5)
-1.9495
CL-USER> (polynomial 0.5)
0.8786454
CL-USER> (polynomial 0.5)
0.07474504
CL-USER> (polynomial 0.5)
0.3032537
CL-USER> (polynomial 0.5)
0.23830011
CL-USER>
what is going on ? I am using the latest sbcl.
* in argument position evaluates to the very last result you had in the REPL. In your code you do (* -2.274 * (expt x 3)) where * is -1.9495 perhaps after the first run. (You'd get an error when running it the first time if the last result was not a number.)
You can have multiple arguments to both * and + and all LISPs has polish prefix notation so your function might look better like this:
;; f(x) = x^4 - 2.274x^3 + 1.8x^2 - 0.576x + 1.0
(defun polynomial (x)
(+ (expt x 4)
(* -2.274 (expt x 3))
(* 1.8 x x)
(* -0.576 x)
1.0)) ;; this was originally 0.1
(polynomial 0.5) ; ==> 0.94025004
Basically x + y + z in infix becomes (+ x y z) in prefix.
Related
I'm trying to write some macros for constraint programming on integers and specifically I'm trying to expand
(int-constr (x y z)
(< 10
(+
(* x 4)
(* y 5)
(* z 6)))
(> 10
(+
(* x 1)
(* y 2)
(* z 3))))
into
(let ((x (in-between 0 1))
(y (in-between 0 1))
(z (in-between 0 1)))
(assert
(and (< 10
(+
(* x 4)
(* y 5)
(* z 6)))
(> 10
(+
(* x 1)
(* y 2)
(* z 3)))))
(list x y z))
When using syntax-rules recursively, I can create nested let at the beginning, but I think I lose the possibility of calling the list of arguments at the end. Is there any way to do it?
Even just sticking to syntax-rules, this macro is easy to write by using ellipses. Here’s an implementation of the behavior you describe:
(define-syntax int-constr
(syntax-rules ()
((_ (x ...) constr ...)
(let ((x (in-between 0 1)) ...)
(assert (and constr ...))
(list x ...)))))
Since ellipses can be used to repeat forms containing pattern variables, not just repeat plain pattern variables on their own, this macro is quite declarative, and it’s both simple to read and write.
(let ((+ *) (* +))
(+ 3 (* 4 5)))
Stepper outs something as:
(define +_0 *)
(define *_0 +)
(+_0 3 (*_0 4 5))
Everything is clear but I why does occur +_0? On my eye it should be:
(define + *)
(define * +)
(+_0 3 (* 4 5))
define isn't exactly the same as let. In a let the values are evaluated before the binding occurs while with define it gets binded to an undefined value and it shadows the original procedures. The expansion makes sure the variables do not shadow the values they are set to by using other symbols in the form.
Try running these:
(let ()
(define + *)
(define * +)
(+ 3 (* 4 5))) ; * and + are undefined so this will fail
(let ()
(define + *)
(define * +)
(list + *)) ; ==> (#<undefined> #<undefined>)
A let (let ((x 10)(* +)) (* x x)) ; ==> 20 should evaluate the same as ((lambda (x *) (* x x)) 10 +) and with this last one you see 10 and + are getting evaluated before they are assigned to x and * inside the procedure.
I am trying to write a recursive code to do x^y but the problem no mater how I update the code it gives me an error.
The Code:
(defun power(x y) (if(> y 0) (* x (power(x (- y 1)))) (1)))
Error:
CL-USER 11 : 5 >Power 2 3
Error: Undefined operator X in form (X (- Y 1)).
Error:
CL-USER 11 : 5 >power(2 3)
Illegal argument in functor position: 2 in (2 3).
You're calling the function in the wrong way. In lisps function calls have the form:
(f a b c)
not
f(a b c)
You had (power (x (- y 1))) in your recursive definition, which in turn had (x (- y 1)) hence the error: x is not a function.
Use (power x (- y 1)) so your definition becomes:
(defun power (x y)
(if (> y 0)
(* x
(power x (- y 1)))
1))
and call it as (power 2 3)
To expand slightly on the previous (correct) answer, this version uses some idiomatic functions:
(defun power (x y)
(if (plusp y)
(* x (power x (1- y)))
1))
You cannot use parenthesis for grouping since CL thinks you want to call function x and function 1. Remove the excess like this:
(defun power(x y)
(if (> y 0)
(* x (power x (- y 1)))
1))
Parenthesis goes on the outside, just as in your function:
(power 2 3) ;==> 8
When you write (X ...) in a Lisp expression, you are asserting that X is a function to be called on the arguments ....
Your problem is you have too many parentheses in your expression. When you write (power (x ..
you've made this assertion. Write (power x ... instead.
You're calling, among others, this code:
(power (x (- y 1)))
So power is called with (x (- y 1)) as a parameter. Are you sure you want to call x as a function?
This works fine:
[1]> ((lambda (x) (/ x x)) 5)
1
but this:
[2]> ((lambda (x y) (/ x y)) 5 2)
5/2
give me '5/2' instead of 2.5. How can I fix it?
Common Lisp performs rational arithmetic whenever possible. If you want floating point, you either have to supplying at least one float as input to the arithmetic function, or use an explicit coercion function on the result.
((lambda (x y) (float (/ x y)) 5 2)
or
((lambda (x y) (/ x y)) 5.0 2)
Rational arithmetic is generally more exact than floating point. Consider this:
(setf x1 (/ 1 3)) => 1/3
(setf x2 (float (/ 1 3)) => 0.33333333
(* x1 3) => 1
(* x2 3) => 0.99999999
Question:
((lambda (x y) (x y)) (lambda (x) (* x x)) (* 3 3))
This was #1 on the midterm, I put "81 9" he thought I forgot to cross one out lawl, so I cross out 81, and he goes aww. Anyways, I dont understand why it's 81.
I understand why (lambda (x) (* x x)) (* 3 3) = 81, but the first lambda I dont understand what the x and y values are there, and what the [body] (x y) does.
So I was hoping someone could explain to me why the first part doesn't seem like it does anything.
This needs some indentation to clarify
((lambda (x y) (x y))
(lambda (x) (* x x))
(* 3 3))
(lambda (x y) (x y)); call x with y as only parameter.
(lambda (x) (* x x)); evaluate to the square of its parameter.
(* 3 3); evaluate to 9
So the whole thing means: "call the square function with the 9 as parameter".
EDIT: The same thing could be written as
((lambda (x) (* x x))
(* 3 3))
I guess the intent of the exercise is to highlight how evaluating a scheme form involves an implicit function application.
Let's look at this again...
((lambda (x y) (x y)) (lambda (x) (* x x)) (* 3 3))
To evaluate a form we evaluate each part of it in turn. We have three elements in our form. This one is on the first (function) position:
(lambda (x y) (x y))
This is a second element of a form and a first argument to the function:
(lambda (x) (* x x))
Last element of the form, so a second argument to the function.
(* 3 3)
Order of evaluation doesn't matter in this case, so let's just start from the left.
(lambda (x y) (x y))
Lambda creates a function, so this evaluates to a function that takes two arguments, x and y, and then applies x to y (in other words, calls x with a single argument y). Let's call this call-1.
(lambda (x) (* x x))
This evaluates to a function that takes a single argument and returns a square of this argument. So we can just call this square.
(* 3 3)
This obviously evaluates to 9.
OK, so after this first run of evaluation we have:
(call-1 square 9)
To evaluate this, we call call-1 with two arguments, square and 9. Applying call-1 gives us:
(square 9)
Since that's what call-1 does - it calls its first argument with its second argument. Now, square of 9 is 81, which is the value of the whole expression.
Perhaps translating that code to Common Lisp helps clarify its behaviour:
((lambda (x y) (funcall x y)) (lambda (x) (* x x)) (* 3 3))
Or even more explicitly:
(funcall (lambda (x y) (funcall x y))
(lambda (x) (* x x))
(* 3 3))
Indeed, that first lambda doesn't do anything useful, since it boils down to:
(funcall (lambda (x) (* x x)) (* 3 3))
which equals
(let ((x (* 3 3)))
(* x x))
equals
(let ((x 9))
(* x x))
equals
(* 9 9)
equals 81.
The answers posted so far are good, so rather than duplicating what they already said, perhaps here is another way you could look at the program:
(define (square x) (* x x))
(define (call-with arg fun) (fun arg))
(call-with (* 3 3) square)
Does it still look strange?