#<Closure> in output - scheme

I was writing a function to switch the last element of a list to the beginning:
(define last-elem
(lambda (l)
(car (reverse l))))
(define all-but-last
(lambda (l)
(reverse (cdr (reverse l)))))
(define (last-to-first x) (append (list last-elem x) (all-but-last x)))
(last-to-first '(1 2 3 4 5 6))
It didn't work and I knew why. I forgot to put the brackets around list last-elem x
The thing is, I was curious about the output of the wrongly-typed code:
(#<Closure> (1 2 3 4 5 6) 1 2 3 4 5)
What is the meaning if this? How did it come out to this?

In Racket, the output is
'(#<procedure:last-elem> (1 2 3 4 5 6) 1 2 3 4 5)
which is a little clearer.
A reference to a function is always stored with its referencing environment, a.k.a. as a closure, and your Scheme implementation chooses to display it that way.

(list last-elem x)
doesn't call the function last-elem. It simply returns a list of two elements: the value of the variable last-elem (which is a procedure) and the value of the argument x. You want:
(list (last-elem x))
But there's no reason to make a list in the first place. Try:
(define (last-to-first x)
(cons (last-elem x) (all-but-last x)))

In Scheme, all identifiers denote either a syntactic keyword (bound to a 'transformer') or a variable (bound to a value). In your code last-elem denotes a variable bound to a function, which you defined. When you write:
(list last-elem x)
the interpreter/compiler produces a list with the value of last-elem and x. Thus, the result of #<Closure> in the list.

Related

Update list in racket without hash

I have the 2 lists, '(1 2 3 4), and '(add1 sub1 add1). They do not have same length. The first list is numbers, the second list is functions. I want to apply the functions to each of element in the number list.
'(1 2 3 4) (add1 sub1 add1) -> '(2 3 4 5) '(sub1 add1)
It look very simple, but I find I can not update the lists. Because in Scheme there is no way to update lists without hash. I can only create new lists. So every time I have to create a new list for each function in the second list. Can someone help me code this question?
Alternatively you could use map and compose in combination.
This is much easier to read and understand.
(map (compose add1 sub1 add1) '(1 2 3 4))
;; '(2 3 4 5)
(compose add1 sub1 add1) chains the functions one after another
and map applies this chained/composed function on each element of the input list '(1 2 3 4).
Generalize to a function:
(define (map-functions funcs . args)
(apply map (apply compose funcs) args))
(map-functions (list add1 sub1 add1) '(1 2 3 4)) ;; '(2 3 4 5)
compose is inbuilt but one can define it like this (% in names to not to overwrite the existing compose.
;; first a compose to compose to functions
(define (%%compose f1 f2)
(lambda args
(f1 (apply f2 args))))
;; then, generalize it for as many functions as one wants (as a variadic function) using `foldl`
(define (%compose . funcs)
(foldl %%compose (car funcs) (cdr funcs)))
You're looking for a left fold. It looks like Racket calls it foldl, which will do the job, combined with map. Something like (Untested, because I don't have Racket installed):
(define functions (list add1 sub1 add1)) ; So you have functions instead of symbols like you get when using quote
(define numbers '(1 2 3 4))
(foldl (lambda (f lst) (map f lst)) numbers functions)
Basically, for each function in that list, it maps the function against the list returned by mapping the previous function (Starting with the initial list of numbers when there is no previous).
If you're stuck with a list of symbols and can't use the (list add1 ... trick to get references to the actual functions, one approach (And I hope there are better ones) is to use eval and some quasiquoting:
(foldl (lambda (f lst) (eval `(map ,f (quote ,lst)))) '(1 2 3 4) '(add1 sub1 add1))

If a list is found in another list?

I started to learn Racket and I don't know how to check if a list is found in another list. Something like (member x (list 1 2 3 x 4 5)), but I want that "x" to be a a sequence of numbers.
I know how to implement recursive, but I would like to know if it exists a more direct operator.
For example I want to know if (list 3 4 5) is found in (list 1 2 3 4 5 6 )
I would take a look at this Racket Object interface and the (is-a? v type) -> boolean seems to be what you are looking for?, simply use it while looping to catch any results that are of a given type and do whatever with them
you may also want to look into (subclass? c cls) -> boolean from the same link, if you want to catch all List types in one go
should there be a possiblity of having a list inside a list, that was already inside a list(1,2,(3,4,(5,6))) i'm afraid that recursion is probally the best solution though, since given there is a possibility of an infinit amount of loops, it is just better to run the recursion on a list everytime you locate a new list in the original list, that way any given number of subList will still be processed
You want to search for succeeding elements in a list:
(define (subseq needle haystack)
(let loop ((index 0)
(cur-needle needle)
(haystack haystack))
(cond ((null? cur-needle) index)
((null? haystack) #f)
((and (equal? (car cur-needle) (car haystack))
(loop index (cdr cur-needle) (cdr haystack)))) ; NB no consequence
(else (loop (add1 index) needle (cdr haystack))))))
This evaluates to the index where the elements of needle is first found in the haystack or #f if it isn't.
You can use regexp-match to check if pattern is a substring of another string by converting both lists of numbers to strings, and comparing them, as such:
(define (member? x lst)
(define (f lst)
(foldr string-append "" (map number->string lst)))
(if (regexp-match (f x) (f lst)) #t #f))
f converts lst (a list of numbers) to a string. regexp-match checks if (f x) is a pattern that appears in (f lst).
For example,
> (member? (list 3 4 5) (list 1 2 3 4 5 6 7))
#t
One can also use some string functions to join the lists and compare them (recursion is needed):
(define (list-in-list l L)
(define (fn ll)
(string-join (map number->string ll))) ; Function to create a string out of list of numbers;
(define ss (fn l)) ; Convert smaller list to string;
(let loop ((L L)) ; Set up recursion and initial value;
(cond
[(empty? L) #f] ; If end of list reached, pattern is not present;
[(string-prefix? (fn L) ss) #t] ; Compare if initial part of main list is same as test list;
[else (loop (rest L))]))) ; If not, loop with first item of list removed;
Testing:
(list-in-list (list 3 4 5) (list 1 2 3 4 5 6 ))
Output:
#t
straight from the Racket documentation:
(member v lst [is-equal?]) → (or/c list? #f)
v : any/c
lst : list?
is-equal? : (any/c any/c -> any/c) = equal?
Locates the first element of lst that is equal? to v. If such an element exists, the tail of lst starting with that element is returned. Otherwise, the result is #f.
Or in your case:
(member '(3 4 5) (list 1 2 3 4 5 6 7))
where x is '(3 4 5) or (list 3 4 5) or (cons 3 4 5)
it will return '(3 4 5 6 7) if x ( searched list '(3 4 5) ) was found in the list or false (#f) if it was not found
or you can use assoc to check if your x is met in one of many lists, or :
(assoc x (list (list 1 2) (list 3 4) (list x 6)))
will return :
'(x 6)
There are also lambda constructions but I will not go in depth since I am not very familiar with Racket yet. Hope this helps :)
EDIT: if member gives you different results than what you expect try using memq instead

multiplying list of items by a certain number 'x'

How would you write a procedure that multiplies each element of the list with a given number (x).If I give a list '(1 2 3) and x=3, the procedure should return (3 6 9)
My try:
(define (mul-list list x)
(if (null? list)
1
(list(* x (car list))(mul-list (cdr list)))))
The above code doesnt seem to work.What changes do I have to make ? Please help
Thanks in advance.
This is the text book example where you should use map, instead of reinventing the wheel:
(define (mul-list lst x)
(map (lambda (n) (* x n)) lst))
But I guess that you want to implement it from scratch. Your code has the following problems:
You should not call list a parameter, that clashes with the built-in procedure of the same name - one that you're currently trying to use!
The base case should return an empty list, given that we're building a list as output
We build lists by consing elements, not by calling list
You forgot to pass the second parameter to the recursive call of mul-list
This should fix all the bugs:
(define (mul-list lst x)
(if (null? lst)
'()
(cons (* x (car lst))
(mul-list (cdr lst) x))))
Either way, it works as expected:
(mul-list '(1 2 3) 3)
=> '(3 6 9)
For and its extensions (for*, for/list, for/first, for/last, for/sum, for/product, for/and, for/or etc: https://docs.racket-lang.org/reference/for.html) are very useful for loops in Racket:
(define (ml2 lst x)
(for/list ((item lst))
(* item x)))
Testing:
(ml2 '(1 2 3) 3)
Output:
'(3 6 9)
I find that in many cases, 'for' implementation provides short, simple and easily understandable code.

Scheme operation on a function

Is it possible to do an operation on a previous function, i have a list of values say (1,2,3,4,5), first function needs to multiply them by 2, while 2nd function adds 1 to result of previous function, so first we would get (2,4,6,8,10), and then (3,5,7,9,11) i got this, function g does extra work, is it possible nstead of doing operations on the element do it on function F or results from function F
#lang racket
(define test (list 1 1 2 3 5))
(define (F)
(map (lambda (element) (* 2 element))
test))
(define (G)
(map (lambda (element) (+ 1 (* 2 element)))
test))
First you need to correctly define your procedures to take a list parameter (called lst in this case):
(define (F lst)
(map (lambda (e) (* 2 e)) lst))
(define (G lst)
(map add1 lst))
Then
> (F '(1 2 3 4 5))
'(2 4 6 8 10)
> (G '(2 4 6 8 10))
'(3 5 7 9 11)
or, if you need to combine both procedures:
> (G (F '(1 2 3 4 5)))
'(3 5 7 9 11)
This is a follow-up to your previous question. As stated in my answer there, you should pass the right parameters to the functions - in particular, pass the input lists as parameter, so you can use the result from one function as input for the next function:
(define test (list 1 1 2 3 5))
(define (multiply-list test)
(map (lambda (element) (* 2 element))
test))
(define (add-list test)
(map (lambda (element) (+ 1 element))
test))
Now, if we want to add one to each element in the input list:
(add-list test)
=> '(3 3 5 7 11)
Or if we want to multiply by two each element in the input list:
(multiply-list test)
=> '(2 2 4 6 10)
And if we want to add one first, then multiply by two we can chain the functions! the result from one becomes the input for the other, and the final result will be as follows:
(multiply-list (add-list test))
=> '(6 6 10 14 22)
NB! You have tagged scheme but you use racket (the language). Not all of my examples will work in scheme.
Yes! you even do it yourself in your definition of G where you add a value and the result of a multiplication.
Its possible to chain map
(map f3 (map f2 (map f1 lst)))
Thus if you instead make a function that takes a list and doubles it:
(define (list-double lst)
(map (lambda (x) (* x 2)) lst))
You can chain it to quadruple it:
(define (list-quadruple lst)
(list-double (list-double lst)))
Now it's not optimal to chain map if you can avoid it. Instead you can compose the procedures together:
(define (double x) (* x 2))
(define (list-quadrouple lst)
(map (compose1 double double) lst))
compose1 here is the same as making a anonymous function where you chain the arguments. Eg. the last would be (lambda (x) (double (double x))). A more complex one compose can do more than one value between procedures. eg. (compose + quotient/remainder)

(scheme) Verify if an element in one list is in the second list with do cicle

How do we verify in scheme with the do cicle, if an element of the first list is in the second?
The do loop in racket has an interesting structure:
(do ([id init-expr step-expr-maybe] ...)
(stop?-expr finish-expr ...)
expr ...)
The documentation for r5rs provides an example:
(let ((x '(1 3 5 7 9)))
(do ((x x (cdr x))
(sum 0 (+ sum (car x))))
((null? x) sum)))
That statement returns 25, the sum of the elements of the loop. The x in the do loop is initialized to the x in the let, and then iteratively set to the cdr of itself each time through the loop. sum is initialized to 0, and accumulates the value of the car of x each time through. The stopping condition is when the iteration variable is empty, and the return value is the sum.
Ok, aside from the racket preference of square brackets, this looks good. There's a do loop and a list. The loop does something over that list. We can use that to write a function that finds a specific atom in a list (using the racket brackets):
(define (find5 lst)
(do ([x lst (rest x)]
[found #f (or found (eq? 5 (first x)))])
((null? x) found)))
Instead of initializing and adding the value sum, I or into found. Also, I prefer first and rest over car and cdr and define them myself when they don't exist. The way this function works should follow from the explanation of the example.
(find5 '(1 2 3 4 6))
Gives #f, as expected. Similarly:
(find5 '(1 2 3 4 5 6))
Gives #t.
Are you able to generalize finding a specific element in a list with a do loop into your specific question?

Resources