Is there a way I can generate multiple values in for/list during each iteration and have the results "flattened"?
For instance:
(for/list ([i (range n)]) (values i (+ i 1)))
I'd like the result to be (list 0 1 1 2 2 3 3 4 ...).
This question is very much relevant to https://github.com/racket/racket/pull/2483. In the link, you will find:
An unmerged PR that lets you write (for/append-list ([i (range n)]) (list i (+ i 1))).
My proposal to let you write (for/list* ([i (range n)]) (values i (+ i 1))) (with caveat, see the link for more details).
But since these don't exist in Racket yet, the easiest way to get what you want is:
(append* (for/list ([i (range n)]) (list i (+ i 1))))
Related
I'm trying to understand what count do.
I have read the documentation, and it says:
Returns (length (filter-map proc lst ...)), but without building the
intermediate list.
Then, I have read filter-map documentation, and it says:
Returns (filter (lambda (x) x) (map proc lst ...)), but without
building the intermediate list.
Then, I have read filter documentation, and I have understand it.
But, I don't understand filter-map. In particular that(lambda (x) x) in (filter (lambda (x) x) (map proc lst ...)).
What is the different between filter and filter-map?
By the way, the examples of filter and filter-map do the same and that make it more difficult to understand them.
I would say that the key insight here is that in the context of filter, you should read (lambda (x) x) as not-false?. So, the documentation for filter-map could be written to read:
Returns (filter not-false? (map proc lst ...)), but without building the intermediate list, where not-false? can be defined as (lambda (x) x).
The whole point is that if you know filter and map well, then you can explain filter-map like that. If you do not know what filter and map does it will not help you understand it. When you need to learn something new you often need to use prior experience. Eg. I can explain multiplication by saying 3 * 4 is the same as 3 + 3 + 3 + 3, but it doesn't help if you don't know what + is.
What is the difference between filter and filter-map
(filter odd? '(1 2 3 4 5)) ; ==> (1 3 5)
(filter-map odd? '(1 2 3 4 5)) ; ==> (#t #t #t))
The first collects the original values from the list when the predicate became truthy. In this case (odd? 1) is true and thus 1 is an element in the result.
filter-map doesn't filter on odd? it works as if you passed odd? to map. There you get a new list with the results.
(map odd? '(1 2 3 4 5)) ; ==> (#t #f #t #f #t #f)
Then it removes the false values so that you only have true values left:
(filter identity (map odd? '(1 2 3 4 5))) ; ==> (#t #t #t)
Now. It's important to understand that in Scheme every value except #f is true.
(lambda (x) x) is the identity function and is the same as identity in #lang racket. It returns its own argument.
(filter identity '(1 #f 2 #f 3)) ; ==> (1 2 3)
count works the same way as filter-map except it only returns how many element you would have got. Thus:
(count odd? '(1 2 3 4 5)) ; ==> 3
Now it mentions that it is the same as:
(length (filter identity (map odd? '(1 2 3 4 5)))
Execpt for the fact that the the code using map, filter, and length like that creates 2 lists. Thus while count does the same it does it without using map and filter. Now it seems this is a primitive, but you could do it like this:
(define (count fn lst)
(let loop ((lst lst) (cnt 0))
(cond ((null? lst) cnt)
((fn (car lst)) (loop (cdr lst) (add1 cnt)))
(else (loop (cdr lst) cnt))))
I am very new to LISP (so forgive me for any dumb mistakes) and the first lab of the year states:
Define a function, STDEV that will compute the standard deviation of a list of numbers (look up formula)
I wrote this code but I don't know why it refuses to work:
(defun stdev (x)
(sqrt (/ (apply '+ (expt (- x (/ (apply '+ x)
(length x)))
2))
(length x))))
(setq a '(1 2 3 4 5))
(STDEV a)
But on runtime it produces the error:
(1 2 3 4 5) is not a number
I believe that I have correctly emulated the standard deviation formula (though I wouldn't put it past myself to make a dumb mistake), but why does my program not like the list of numbers that I give it to evaluate? It is most likely a simple mistake with inputs from this new style of coding but any and all help is greatly appreciated!
Use indentation. I've edited your question:
(defun stdev (x)
(sqrt (/ (apply '+ (expt (- x (/ (apply '+ x)
(length x)))
2))
(length x))))
expt returns a number. You call (apply '+ some-number)?
Also you subtract a number from a list.
Why?
Generally I would recommend to use a Lisp listener (aka REPL) to get to working code:
Compute the mean value:
CL-USER 21 > (let ((l (list 1 2 3 4 5)))
(/ (reduce #'+ l)
(length l)))
3
Subtract the mean value and square using mapcar:
CL-USER 22 > (mapcar (lambda (item)
(expt (- item 3) 2))
(list 1 2 3 4 5))
(4 1 0 1 4)
Compute the variance as the mean value of above:
CL-USER 23 > (let ((l (list 4 1 0 1 4)))
(/ (reduce #'+ l)
(length l)))
2
Take the square root to get the standard deviation:
CL-USER 24 > (sqrt 2)
1.4142135
Then you only need to assemble it into a few functions: average, variance and standard-deviation.
You’re taking - a ..., when a is your list.
Not a complete answer, because this is homework, but: you want to calculate the mean first, you can implement a sum function, which you will need twice, with a fold, and you can apply a helper function or lambda expression to every element of a list using a map.
I am struggling to find the right approach to solve the following function
(FOO #'– '(1 2 3 4 5))
=> ((–1 2 3 4 5) (1 –2 3 4 5) (1 2 –3 4 5) (1 2 3 –4 5) (1 2 3 4 –5))
The first Parameter to the foo function is supposed to be a function "-" that has to be applied to each element returning a list of list as shown above. I am not sure as to what approach I can take to create this function. I thought of recursion but not sure how I will preserve the list in each call and what kind of base criteria would I have. Any help would be appreciated. I cannot use loops as this is functional programming.
It's a pity you cannot use loop because this could be elegantly solved like so:
(defun foo (fctn lst)
(loop
for n from 0 below (length lst) ; outer
collect (loop
for elt in lst ; inner
for i from 0
collect (if (= i n) (funcall fctn elt) elt))))
So we've got an outer loop that increments n from 0 to (length lst) excluded, and an inner loop that will copy verbatim the list except for element n where fctn is applied:
CL-USER> (foo #'- '(1 2 3 4 5))
((-1 2 3 4 5) (1 -2 3 4 5) (1 2 -3 4 5) (1 2 3 -4 5) (1 2 3 4 -5))
Replacing loop by recursion means creating local functions by using labels that replace the inner and the outer loop, for example:
(defun foo (fctn lst)
(let ((len (length lst)))
(labels
((inner (lst n &optional (i 0))
(unless (= i len)
(cons (if (= i n) (funcall fctn (car lst)) (car lst))
(inner (cdr lst) n (1+ i)))))
(outer (&optional (i 0))
(unless (= i len)
(cons (inner lst i) (outer (1+ i))))))
(outer))))
Part of the implementation strategy that you choose here will depend on whether you want to support structure sharing or not. Some of the answers have provided solutions where you get completely new lists, which may be what you want. If you want to actually share some of the common structure, you can do that too, with a solution like this. (Note: I'm using first/rest/list* in preference to car/car/cons, since we're working with lists, not arbitrary trees.)
(defun foo (operation list)
(labels ((foo% (left right result)
(if (endp right)
(nreverse result)
(let* ((x (first right))
(ox (funcall operation x)))
(foo% (list* x left)
(rest right)
(list* (revappend left
(list* ox (rest right)))
result))))))
(foo% '() list '())))
The idea is to walk down list once, keeping track of the left side (in reverse) and the right side as we've gone through them, so we get as left and right:
() (1 2 3 4)
(1) (2 3 4)
(2 1) (3 4)
(3 2 1) (4)
(4 3 2 1) ()
At each step but the last, we take the the first element from the right side, apply the operation, and create a new list use revappend with the left, the result of the operation, and the rest of right. The results from all those operations are accumulated in result (in reverse order). At the end, we simply return result, reversed. We can check that this has the right result, along with observing the structure sharing:
CL-USER> (foo '- '(1 2 3 4 5))
((-1 2 3 4 5) (1 -2 3 4 5) (1 2 -3 4 5) (1 2 3 -4 5) (1 2 3 4 -5))
By setting *print-circle* to true, we can see the structure sharing:
CL-USER> (setf *print-circle* t)
T
CL-USER> (let ((l '(1 2 3 4 5)))
(list l (foo '- l)))
((1 . #1=(2 . #2=(3 . #3=(4 . #4=(5))))) ; input L
((-1 . #1#)
(1 -2 . #2#)
(1 2 -3 . #3#)
(1 2 3 -4 . #4#)
(1 2 3 4 -5)))
Each list in the output shares as much structure with the original input list as possible.
I find it easier, conceptually, to write some of these kind of functions recursively, using labels, but Common Lisp doesn't guarantee tail call optimization, so it's worth writing this iteratively, too. Here's one way that could be done:
(defun phoo (operation list)
(do ((left '())
(right list)
(result '()))
((endp right)
(nreverse result))
(let* ((x (pop right))
(ox (funcall operation x)))
(push (revappend left (list* ox right)) result)
(push x left))))
The base case of a recursion can be determined by asking yourself "When do I want to stop?".
As an example, when I want to compute the sum of an integer and all positive integers below it, I can do this recusively with a base case determined by answering "When do I want to stop?" with "When the value I might add in is zero.":
(defun sumdown (val)
(if (zerop val)
0
(+ (sumdown (1- val)) val)))
With regard to 'preserve the list in each call', rather than trying to preserve anything I would just build up a result as you go along. Using the 'sumdown' example, this can be done in various ways that are all fundamentally the same approach.
The approach is to have an auxiliary function with a result argument that lets you build up a result as you recurse, and a function that is intended for the user to call, which calls the auxiliary function:
(defun sumdown1-aux (val result)
(if (zerop val)
result
(sumdown1-aux (1- val) (+ val result))))
(defun sumdown1 (val)
(sumdown1-aux val 0))
You can combine the auxiliary function and the function intended to be called by the user by using optional arguments:
(defun sumdown2 (val &optional (result 0))
(if (zerop val)
result
(sumdown2 (1- val) (+ val result))))
You can hide the fact that an auxiliary function is being used by locally binding it within the function the user would call:
(defun sumdown3 (val)
(labels ((sumdown3-aux (val result)
(if (zerop val)
result
(sumdown3-aux (1- val) (+ val result)))))
(sumdown3-aux val 0)))
A recursive solution to your problem can be implemented by answering the question "When do I want to stop when I want to operate on every element of a list?" to determine the base case, and building up a result list-of-lists (instead of adding as in the example) as you recurse. Breaking the problem into smaller pieces will help - "Make a copy of the original list with the nth element replaced by the result of calling the function on that element" can be considered a subproblem, so you might want to write a function that does that first, then use that function to write a function that solves the whole problem. It will be easier if you are allowed to use functions like mapcar and substitute or substitute-if, but if you are not, then you can write equivalents yourself out of what you are allowed to use.
I am trying to write a function that takes one or more integers and returns a list of all the arguments that have the same even-odd parity as the first argument, for example
(same-parity 1 2 3 4 5 6 7)->(1 3 5 7)
(same-parity 2 3 4 5 6)->(2 4 6).
my code is
(define (same-parity g . w)
(define (iter-parity items)
(if (= (length items) 1)
(if (= (remainder items 2) (remainder g 2))
item
'())
(if (= (remainder g 2) (remainder (car items) 2))
(cons (car items) (iter-parity (cdr items)))
(iter-parity (cdr items)))))
(cons g (iter-parity w)))
when try this (same-parity (list 1 2 3 4)), I got an error message:
the object (), passed as the first argument to car, is not the correct type.
Can I somebody tell me what is going on?
Your code
Here's a refactoring proposal, keeping with your basic structure:
(define (same-parity g . w)
(define filter-predicate? (if (odd? g) odd? even?))
(define (iter-parity items)
(if (null? items)
'()
(if (filter-predicate? (car items))
(cons (car items) (iter-parity (cdr items)))
(iter-parity (cdr items)))))
(cons g (iter-parity w)))
Note that it is more idiomatic
to use the procedures odd? and even? rather than remainder
to have as a base case when the list is empty, not when it has only one item (in your code this clearly avoids repetition as a positive effect).
Also, since there is a built-in filter procedure in Scheme, you could express it as follows:
(define (same-parity g . w)
(cons g (filter (if (odd? g) odd? even?) w)))
Your question
As for your question regarding (same-parity (list 1 2 3 4)): you need either (as described in your specification) use your procedure like so
(same-parity 1 2 3 4)
or to use apply here:
> (apply same-parity (list 1 2 3 4))
'(1 3)
because apply will transform (same-parity (list 1 2 3 4)) (1 parameter, a list) into (same-parity 1 2 3 4) (4 parameters).
I have written the following program to calculate the sum of all multiples of 3 & 5 below 1000 in scheme. However, it gives me an incorrect output.
Any help would be much appreciated.
(define (multiples)
(define (calc a sum ctr cir)
(cond (> a 1000) (sum)
(= ctr 7) (calc (+ a (list-ref cir 0)) (+ sum a) 0 (list 3 2 1 3 1 2 3))
(else (calc (+ a (list-ref cir ctr)) (+ sum a) (+ 1 ctr) (list 3 2 1 3 1 2 3)))))
(calc 0 0 0 (list 3 2 1 3 1 2 3)))
You can simply port imperative style solution to functional Scheme by using an accumulator(sum parameter) and a target parameter to test when to stop summing:
(define (multiples)
(define (multiples-iter num sum target)
(if (> num target)
sum
(multiples-iter (+ 1 num)
(if (or (zero? (mod num 3)) (zero? (mod num 5)))
(+ sum num)
sum)
target)))
(multiples-iter 0 0 1000))
Here's my (Racket-specific) solution, which doesn't involve lots of (or, for that matter, any) modulo calls, and is completely general (so that you don't need to construct the (3 2 1 3 1 2 3) list that the OP has):
(define (sum-of-multiples a b limit)
(define (sum-of-multiple x)
(for/fold ((sum 0))
((i (in-range 0 limit x)))
(+ sum i)))
(- (+ (sum-of-multiple a) (sum-of-multiple b))
(sum-of-multiple (lcm a b))))
Test run:
> (sum-of-multiples 3 5 1000)
233168
If you're using Racket, there's a very compact way to do what you ask, using looping constructs:
(for/fold ([sum 0])
([i (in-range 1 1000)]
#:when (or (zero? (modulo i 3)) (zero? (modulo i 5))))
(+ sum i))
=> 233168
One problem is that your code is missing a pair of parentheses around the cond clauses.
In the line (cond (> a 1000) (sum) the condition is just> while a and 1000 are interpreted as forms to be evaluated if > is true (which it is), and thus 1000 will be returned as the result.
Two other problem (masked by the first one) is that you are initializing ctr to 0 when it reaches 7, while it should be set to the next value, i.e. 1, and that you are including 1000 in the result.
The corrected version of your function is
(define (multiples)
(define (calc a sum ctr cir)
(cond ((>= a 1000) sum)
((= ctr 7) (calc (+ a (list-ref cir 0)) (+ sum a) 1 (list 3 2 1 3 1 2 3)))
(else (calc (+ a (list-ref cir ctr)) (+ sum a) (+ 1 ctr) (list 3 2 1 3 1 2 3)))))
(calc 0 0 0 (list 3 2 1 3 1 2 3)))
The same algorithm can also be defined as a non-recursive function like this:
(define (multiples)
(do ((cir (list 3 2 1 3 1 2 3))
(ctr 0 (+ ctr 1))
(a 0 (+ a (list-ref cir (modulo ctr 7))))
(sum 0 (+ sum a)))
((>= a 1000) sum)))
(require-extension (srfi 1))
(define (sum-mod-3-5 upto)
(define (%sum-mod-3-5 so-far generator-position steps)
(let ((next (car generator-position)))
(if (> (+ steps next) upto)
so-far
(%sum-mod-3-5 (+ so-far steps)
(cdr generator-position)
(+ steps next)))))
(%sum-mod-3-5 0 (circular-list 3 2 1 3 1 2 3) 0)) ; 233168
For this particular task, it will do on average half the operations then you would do if incrementing the counter by one, also, one less if condition to check.
Also, modulo (as being division in disguise, probably) is more expensive then summation.
EDIT: I'm not a pro on modular system in different dialects of Scheme. The SRFI-1 extension here is only required to make it easier to create a circular list. I couldn't find an analogue to Common Lisp (#0=(3 2 1 3 1 2 3) . #0#), but perhaps, someone more knowledgeable will correct this.
If you absolutely want to use the "repeating pattern" method, you could go about it something like this.
This uses recursion on the list of intervals rather than relying on list-ref and explicit indexing.
(define (mults limit)
(define steps '(3 2 1 3 1 2 3))
(define (mults-help a sum ls)
(cond ((>= a limit) sum)
((null? ls) (mults-help a sum steps))
(else (mults-help (+ a (car ls))
(+ a sum)
(cdr ls)))))
(mults-help 0 0 steps))