A function is defined in ACL2, and we are tasked with creating a measure function to help prove termination. This is the function definition:
(defunc f (x a)
:input-contract (and (integerp x) (listp a))
:output-contract (integerp (f x a))
(cond
((endp a) 68)
((equal (len a) x) 71)
((equal (len a) (+ x 1)) 74)
((< x (len a)) (f (+ x 1) (rest a)))
(t (f (- x 1) (cons 1 a)))))
And a solution measure function is this (in shorthand):
(m x a) = (if (equal (len a) (+ x 1))
0
(abs (- (len a) x)))
We were able to determine the else case of the measure function would be included, based on the two recursive calls in the function. However, we don't understand the rest of it, and the process that went into figuring out this measure function.
For reference, a measure function:
m is an admissible function defined over the parameters of f;
m has the same input contract as f;
m has an output contract stating that it always returns a natural number; and
on every recursive call, m applied to the arguments to that recursive call decreases,
under the conditions that led to the recursive call.
What is the process that led to determining this measure function?
When determining a measure function, the question to ask yourself is: What is the "potential energy" that gets used up on each iteration, to the point where at some point it's all gone and the iteration stops?
The first place to look is usually the termination conditions. In this case there are three, but the last two are the most interesting: they say we stop iterating if the difference between x and (len a) is too small.
That gives us an idea: what if the potential energy is difference between (len a) and x? To see whether that makes sense, we need to check the recursive cases and make sure that each one of them uses up some energy, i.e. decreases the difference. Things look pretty good here:
If x is less than (len a) we increase x by 1 and decrease (len a) by 1. So if the difference between them was n, then on the next iteration it will be n-2 unless x = (len a) - 1.
Otherwise x is greater than (len a) and we decrease x by 1 and increase (len a) by 1. Again, if the difference between them was n, then on the next iteration it will be n-2 unless x = (len a) + 1.
From there it's pretty easy to see that we should choose x = (len a) + 1 as our "low energy state", since it handles the pesky detail of those two unless clauses.
Related
I'm trying to get the hang of recursion in scheme. I put together a Fibinachi function and it keeps returning unspecified instead of a number. How do I make this function return a number and to unspecified?
(define (F n)
(if (= n 0)
0)
(if (= n 1)
1)
(if (< n 2)
(+
(F (- n 1))
(F (- n 2)))))
(display (F 5))
(newline)
The function returns
#<unspecified>
I'm using guile (GNU Guile) 2.0.13.
The issue here is that your code is:
(begin
(if a 1)
(if b 2)
(if c 3))
What is wrong with this? The value of that will be unspecified except if c is true.
Why? The value of each if is unspecified when the condition is false. The begin returns the value of the last expression.
Where did the begin come from you might ask as it didn't appear in my code? To make it easier every lambda and define contains an implicit begin which is why your code was even accepted for execution.
You should use either nested ifs or a cond form:
(if a 1
(if b 2
(if c 3)))
(cond (a 1)
(b 2)
(c 3))
So, I have three procedures.
(define (addition a)
(+ a 1))
(define (subtraction b)
(- b 1))
(define (recursion a b)
(define a 10)
(define b 0)
(if (a > 0)
(sub1 a)
(add1 b))
(if (b > 0)
(sub1 b)
(add1 a))
0)
The first one takes an integer and adds 1 to it. The second one takes an integer and subtracts 1 from it. The third one is supposed to use these two methods and a recursive way, so if I give (recursion 3 0) as input, it should subtract 1 from 3 until it's 0, and add 1 to 0 until it's 3. As you can see, this code isn't running...
I think the base case would be when a reaches 0 or in the other case b reaches 0. Right?
You first two functions have no issues. They're the classic inc and dec functions. Inc for increment and dec for decrement.
Your "recursion" function should not take a and b as arguments and then set their values with define. Generally, you should not set values with define inside a function in scheme (there are lets to do this, and, in this case, it's not necessary). So drop the (define a something) (define b something).
The main problem with the function "recursion" is that it's not recursive.
A recursive function calls itself. For instance, lets say I recreate your first two functions.
(define (inc a) (+ a 1))
(define (dec a) (+ a 1))
Then I create another function called recursion, but I'll just use one variable for this demo. Let's say that "recursion" will take the number "a".
If a = 5, we just return a . <=== base case
If a < 5, we increment a AND call ourself on the new a . <= recursive case
If a > 5, we decrement a AND call ourself on the new a . <= recursive case
(define (recursion a)
(if (= a 5)
a
(if (< a 5)
(recursion (inc a))
(recursion (dec a)))))
To be really fair, moving toward a central base case is generally not what you want to do. You should be thinking about 'consuming' your input. 0, the empty list, or nil, or good base cases. Anything can be a base case, but these values tend to guild your thinking toward a clear algorithm.
Does that help?
In class we talked about two functions in racket i-e letcc and throw. The instructor said that let/cc has something to do with calling with the current continuation and throw just applies a to b e.g.
(throw a b)
I haven't been able to find much about these online. I did find a question asked for letcc on stackoverflow but I have not been able to understand the functioning of letcc from it completely. Could someone explain these two in simple words along with a simple example?
Edit1: Also in my practice mid exam we are given two question related to it.
For each of the following expressions that contain uses of let/cc, what is the value of each expression?
(let/cc k (throw (throw k 5) 6))
(let/cc k (throw k ((( lambda (x) x) k) (∗ 5 5))))
The answers to these are 5 and 25 respectively. I just wanna understand the two concepts so that I can work with questions like these in my midterm exam.
Let's look at let/cc first.
The expression (let/cc k e) will 1) capture the current continuation (represented as a function) then 2) bind the variable k to the captured continuation and finally 3) evaluate the expression e.
A few examples are in order.
If during evaluation of the expression e, the captured contination k is not called, then the value of the let/cc expression is simply the value(s) to which the expression e evaluated to.
> (+ 10 (let/cc k 32))
42
If on the other hand k is called with a value v then the value of the entire let\cc expression becomes v.
> (+ 10 (let/cc k (+ 1 (k 2))))
12
Notice that the part (+ _) around the call (k 2) is skipped.
The value is return to the continuation of (let/cc ...) immediately.
The most common use of let/cc is to mimic the control struct return known from many statement based languages. Here is the classical is-it-a-leap-year problem:
(define (divisible-by? y k)
(zero? (remainder y k)))
(define (leap-year? y)
(let/cc return
(when (not (divisible-by? y 4))
(return #f))
(when (not (divisible-by? y 100))
(return #t))
(when (not (divisible-by? y 400))
(return #f))
#t))
(for/list ([y (in-range 1898 1906)])
(list y (leap-year? y)))
Now what about throw ? That depends on which throw we are talking about.
Is it the one from misc1/throw ?
Or perhaps the one from Might's article? http://matt.might.net/articles/programming-with-continuations--exceptions-backtracking-search-threads-generators-coroutines/
Or perhaps you are using the definition
(define (throw k v)
(k v))
If the latter, then you can replace (k v) in my examples with (throw k v).
UPDATE
Note that the continuation bound to k can be used more than once - it can also be used outside the let/cc expression. Consider this example:
(define n 0)
(let ([K (let/cc k k)])
(when (< n 10)
(displayln n)
(set! n (+ n 1))
(K K)))
Can you figure out what it does without running it?
Here is a "step by step" evaluation of the nested let/cc example.
(let/cc k0
((let/cc k1
(k0 (sub1 (let/cc k2
(k1 k2)))))
1))
(let/cc k0
(k2 1))
(let/cc k0
((let/cc k1
(k0 (sub1 1)))
1))
(let/cc k0
((let/cc k1
(k0 0))
1))
0
I am still new in racket language.
I am implementing a switch case in racket but it is not working.
So, I shift into using the equal and condition. I want to know how can i call a function that takes input. for example: factorial(n) function
I want to call it in :
(if (= c 1) (factorial (n))
There are two syntax problems with this snippet:
(if (= c 1) (factorial (n)))
For starters, an if expression in Racket needs three parts:
(if <condition> <consequent> <alternative>)
The first thing to fix would be to provide an expression that will be executed when c equals 1, and another that will run if c is not equal to 1. Say, something like this:
(if (= c 1) 1 (factorial (n)))
Now the second problem: in Scheme, when you surround a symbol with parentheses it means that you're trying to execute a function. So if you write (n), the interpreter believes that n is a function with no arguments and that you're trying to call it. To fix this, simply remove the () around n:
(if (= c 1) 1 (factorial n))
Now that the syntax problems are out of the way, let's examine the logic. In Scheme, we normally use recursion to express solutions, but a recursion has to advance at some point, so it will eventually end. If you keep passing the same parameter to the recursion, without modifying it, you'll get caught in an infinite loop. Here's the proper way to write a recursive factorial procedure:
(define (factorial n)
(if (<= n 0) ; base case: if n <= 0
1 ; then return 1
(* n (factorial (- n 1))))) ; otherwise multiply and advance recursion
Notice how we decrement n at each step, to make sure that it will eventually reach zero, ending the recursion. Once you get comfortable with this solution, we can think of making it better. Read about tail recursion, see how the compiler will optimize our loops as long as we write them in such a way that the last thing done on each execution path is the recursive call, with nothing left to do after it. For instance, the previous code can be written more efficiently as follows, and see how we pass the accumulated answer in a parameter:
(define (factorial n)
(let loop ([n n] [acc 1])
(if (<= n 0)
acc
(loop (- n 1) (* n acc)))))
UPDATE
After taking a look at the comments, I see that you want to implement a switchcase procedure. Once again, there are problems with the way you're declaring functions. This is wrong:
(define fact(x)
The correct way is this:
(define (fact x)
And for actually implementing switchcase, it's possible to use nested ifs as you attempted, but that's not the best way. Learn how to use the cond expression or the case expression, either one will make your solution simpler. And anyway you have to provide an additional condition, in case c is neither 1 nor 2. Also, you're confounding the parameter name - is it c or x? With all the recommendations in place, here's how your code should look:
(define (switchcase c)
(cond ((= c 1) (fact c))
((= c 2) (triple c))
(else (error "unknown value" c))))
In racket-lang, conditionals with if has syntax:
(if <expr> <expr> <expr>)
So in your case, you have to provide another <expr>.
(define (factorial n)
(if (= n 1) 1 (* n (factorial (- n 1)))))
;^exp ^exp ^exp
(factorial 3)
The results would be 6
Update:
(define (factorial n)
(if (= n 1) 1 (* n (factorial (- n 1)))))
(define (triple x)
(* 3 x))
(define (switchcase c)
(if (= c 1)
(factorial c)
(if(= c 2)
(triple c) "c is not 1 or 2")))
(switchcase 2)
If you want something a lot closer to a switch case given you can return procedures.
(define (switch input cases)
(let ((lookup (assoc input cases)))
(if lookup
(cdr lookup)
(error "Undefined case on " input " in " cases))))
(define (this-switch c)
(let ((cases (list (cons 1 triple)
(cons 2 factorial))))
((switch c cases) c)))
My solution to exercise 1.11 of SICP is:
(define (f n)
(if (< n 3)
n
(+ (f (- n 1)) (* 2 (f (- n 2))) (* 3 (f (- n 3))))
))
As expected, a evaluation such as (f 100) takes a long time. I was wondering if there was a way to improve this code (without foregoing the recursion), and/or take advantage of multi-core box. I am using 'mit-scheme'.
The exercise tells you to write two functions, one that computes f "by means of a recursive process", and another that computes f "by means of an iterative process". You did the recursive one. Since this function is very similar to the fib function given in the examples of the section you linked to, you should be able to figure this out by looking at the recursive and iterative examples of the fib function:
; Recursive
(define (fib n)
(cond ((= n 0) 0)
((= n 1) 1)
(else (+ (fib (- n 1))
(fib (- n 2))))))
; Iterative
(define (fib n)
(fib-iter 1 0 n))
(define (fib-iter a b count)
(if (= count 0)
b
(fib-iter (+ a b) a (- count 1))))
In this case you would define an f-iter function which would take a, b, and c arguments as well as a count argument.
Here is the f-iter function. Notice the similarity to fib-iter:
(define (f-iter a b c count)
(if (= count 0)
c
(f-iter (+ a (* 2 b) (* 3 c)) a b (- count 1))))
And through a little trial and error, I found that a, b, and c should be initialized to 2, 1, and 0 respectively, which also follows the pattern of the fib function initializing a and b to 1 and 0. So f looks like this:
(define (f n)
(f-iter 2 1 0 n))
Note: f-iter is still a recursive function but because of the way Scheme works, it runs as an iterative process and runs in O(n) time and O(1) space, unlike your code which is not only a recursive function but a recursive process. I believe this is what the author of Exercise 1.1 was looking for.
I'm not sure how best to code it in Scheme, but a common technique to improve speed on something like this would be to use memoization. In a nutshell, the idea is to cache the result of f(p) (possibly for every p seen, or possibly the last n values) so that next time you call f(p), the saved result is returned, rather than being recalculated. In general, the cache would be a map from a tuple (representing the input arguments) to the return type.
Well, if you ask me, think like a mathematician. I can't read scheme, but if you're coding a Fibonacci function, instead of defining it recursively, solve the recurrence and define it with a closed form. For the Fibonacci sequence, the closed form can be found here for example. That'll be MUCH faster.
edit: oops, didn't see that you said forgoing getting rid of the recursion. In that case, your options are much more limited.
See this article for a good tutorial on developing a fast Fibonacci function with functional programming. It uses Common LISP, which is slightly different from Scheme in some aspects, but you should be able to get by with it. Your implementation is equivalent to the bogo-fig function near the top of the file.
To put it another way:
To get tail recursion, the recursive call has to be the very last thing the procedure does.
Your recursive calls are embedded within the * and + expressions, so they are not tail calls (since the * and + are evaluated after the recursive call.)
Jeremy Ruten's version of f-iter is tail-recursive rather than iterative (i.e. it looks like a recursive procedure but is as efficient as the iterative equivalent.)
However you can make the iteration explicit:
(define (f n)
(let iter
((a 2) (b 1) (c 0) (count n))
(if (<= count 0)
c
(iter (+ a (* 2 b) (* 3 c)) a b (- count 1)))))
or
(define (f n)
(do
((a 2 (+ a (* 2 b) (* 3 c)))
(b 1 a)
(c 0 b)
(count n (- count 1)))
((<= count 0) c)))
That particular exercise can be solved by using tail recursion - instead of waiting for each recursive call to return (as is the case in the straightforward solution you present), you can accumulate the answer in a parameter, in such a way that the recursion behaves exactly the same as an iteration in terms of the space it consumes. For instance:
(define (f n)
(define (iter a b c count)
(if (zero? count)
c
(iter (+ a (* 2 b) (* 3 c))
a
b
(- count 1))))
(if (< n 3)
n
(iter 2 1 0 n)))