i need help with racket
(define size1 (lambda (m)
(printf "size is ~v" (length m))))
test it
>(size1 '(2 8 9 0 'uu 98 0))
size is 7
which is fine
,
but second test
> (size1 '((((7) 9 (11)))))
size is 1
it is give me that 1, cuz of the brocket, However
what i want to provide is 3
i need help with that
Note the following:
'((((7) 9 (11)))) ; list with one element --> '(((7) 9 (11)))
'(((7) 9 (11))) ; list with one element --> '((7) 9 (11))
'((7) 9 (11)) ; list with 3 elements --> '(7), 9 and '(11)
If you intended to write a list with three elements, then your list should be '((7) 9 (11)), and your function call becomes:
> (size1 '((7) 9 (11)))
size is 3
So you would like to count the elements that are not null and not pairs:
(define (count-atoms tree)
(cond ((null? tree) 0) ; an empty tree has 0 atoms
((not (pair? tree)) 1) ; an atom is exactly one atom
(else ???))) ; the sum of counting atoms in car and cdr
This is very similar to how length is made.
Related
I want to pick a random element from list1, remove it from list1, and add it to list2.
(define list1 '(1 2 3 4 5 6 7 8)
(define list2 '(9 10)
Now my problem is, that i use 2 functions to update the lists.
list1 will get a random element removed and list2 will get a random element appended but its not always the same element.
How can I make it that list2 gets the element added, that list1 got removed and then repeat these steps until list1 is empty?
Thanks a lot in advance
#lang racket
(define list1 '(1 2 3 4 5 6 7 8))
(define list2 '(9 10))
(define (select_random list)
(car (shuffle list)))
(define (update_list list)
(remove (select_random list) list))
(define (addToList list1 target_list)
(append (list (select_random list1)) target_list))
The way to select one element at random to be used several places is to do it outside of the functions:
(define (select-random lst)
(car (shuffle lst)))
Now you need to use the element to do your stuff:
(define (remove-element element lst)
(remove element lst))
(define (add-element element lst)
(cons element lst))
So in your loop you can do something like this:
(let loop ((list1 '(1 2 3 4 5 6 7 8 9 10))
(list2 '()))
(if (null? list1)
list2
(let ((element (select-random list1)))
(loop (remove-element element list1)
(add-element element list2)))))
; ==> (2 1 5 4 10 7 6 8 9 3)
Notice that remove-element and add-element are really just synonyms for remove and cons. They don't add any value but change the name. Thus you can just omit them:
(let loop ((list1 '(1 2 3 4 5 6 7 8 9 10))
(list2 '()))
(if (null? list1)
list2
(let ((element (select-random list1)))
(loop (remove element list1)
(cons element list2)))))
In reality this is just a very complicated way to do (shuffle '(1 2 3 4 5 6 7 8 9 10)).
Let's say we have a: (list 1 2 3 5 2 6 7 4)
I want to know if 2 appears at least twice.
member? checks if it appears at all. I suppose I could check member? then run remove then check member? again. Is there a more efficient method?
You should use count, which receives a lambda for checking any condition you want and a list to be checked. It returns the number of elements in the list that meet the condition:
(count (lambda (n) (= n 2)) (list 1 2 3 5 2 6 7 4))
=> 2
Then it's a simple matter to verify if the count fulfills the requirement that the number appears at least twice.
One can use member function with recursion to check if first element is the desired number and is also part of rest of the list- then loop again with rest of the list:
(define (is_duplicated n L)
(let loop ((L L))
(cond
[(empty? L) #f]
[(and (= n (first L))
(member n (rest L))) #t]
[else (loop (rest L))]
)))
(is_duplicated 2 (list 1 2 3 5 2 6 7 4))
Note that it is "member" and not "member?" which is part of Racket base functions (https://docs.racket-lang.org/search/index.html?q=member%3F).
I’m trying to write a function with two arguments of this type:
substitutions (list_one, list_two)
list_one has always this form (letters can change according to the input):
(1 ((1 2 ((1 2 r) (3 2 t) (4 3 c))) (3 4 ((5 6 y) (5 7 i)))))
list_two has always this form (numbers can change according to the input):
(2 3 4 5 6)
I want to substitute in this way:
r-> 2
t -> 3
c -> 4
y -> 5
i -> 6
Can you help me please?
A not so efficient solution is to first find a list of all the letters in the fist tree structure (the first list) and then to LOOP over the results calling SUBST repeatedly.
To find the list of non numeric atoms in the first list (the 'letters') you need to traverse the tree structure (le first list) recurring both on the FIRST and on the REST of the list.
Hope it helps.
MA
If the lists are proper you can iterate them with the loop macro and pop off the arguments in the accessible free variable:
(defun template-replace (template replacements)
(labels ((iterate (template)
(loop :for element :in template
:collect
(cond ((consp element) (iterate element))
((symbolp element) (pop replacements))
(t element)))))
(iterate template)))
(template-replace '(1 rep (4 rep (9 rep)) rep) '(foot inch mm multiplied))
; ==> (1 foot (4 inch (9 mm)) multiplied)
I'm taking an intro to computer science course and one question needs me to write a function that takes a list of numbers and a number and returns the numbers in the list whose sum is less than the given number. I've written the function signature, definition, and check-expects, but I'm stuck. The function needs to assume intermediate student with lambda. I don't want any direct answers here; just help so that I can reach the answer myself.
I know it needs to use recursion. Perhaps a helper function would be needed.
;; sum-up-to: lon, number -> lon
;; consumes a list of numbers and a number and
;; returns the numbers in the list whose sum is
;; less than or equal to the given number
(define the-numbers (list 1 2 3 4 5 6 7 8 9))
(check-expect (sum-up-to the-numbers 7) (list 1 2 3))
(check-expect (sum-up-to the-numbers 18) (list 1 2 3 4 5))
(check-expect (sum-up-to the-numbers 45) the-numbers)
This problem can be simplified if we sort the list first and if we define a helper function that keeps track of the accumulated sum. Here's a skeleton, fill-in the blanks with the missing expressions and you'll have the solution:
(define (sum-up-to lst n)
(helper <???> n 0)) ; sort the input list, pass it to the helper
(define (helper lst n sum)
(cond (<???> '()) ; if the list is empty, end the recursion
((> <???> n) '()) ; also end recursion if sum + current element > n
(else
(cons <???> ; otherwise cons current element
(helper <???> ; advance recursion over list
n
(+ <???> <???>)))))) ; update sum
Following recursive method keeps adding numbers from the list sequentially to an initially empty outlist, till the sum is reached:
(define the-numbers (list 1 2 3 4 5 6 7 8 9))
(define (f lst sum)
(let loop ((lst lst)
(ol '()))
(if (or (..ENTER CONDITION FOR EMPTY LIST..)
(..ENTER CONDITION WHEN SUM IS REACHED..)
(..ENTER HOW TO PUT THE NEW LIST OUT..)
(loop (..ENTER ARGUMENTS TO BE SENT TO NEXT LOOP..)
))))
(f the-numbers 7)
(f the-numbers 18)
(f the-numbers 45)
Output:
'(1 2 3)
'(1 2 3 4 5)
'(1 2 3 4 5 6 7 8 9)
I am working using a visual programming environment for musical composition based on CL . I am trying to create a function that when given say 3 elements (1 2 3) will return 1, 2, 3, 1, 2, 3 etc., one number at the time each time it is evaluated. The book Common Lisp a Gentle Introduction, mentions briefly that it's possible to create circular lists using sharp-equal notation but does not get into details on how to use them.
Keep in mind that I can insert actual Lisp code in the program using a object specifically designed for that.
CL-USER 3 > (defun circular (items)
(setf (cdr (last items)) items)
items)
CIRCULAR
CL-USER 4 > (setf *print-circle* t)
T
CL-USER 5 > (circular (list 1 2 3))
#1=(1 2 3 . #1#)
Example:
CL-USER 16 > (setf c1 (circular (list 1 2 3)))
#1=(1 2 3 . #1#)
CL-USER 17 > (pop c1)
1
CL-USER 18 > (pop c1)
2
CL-USER 19 > (pop c1)
3
CL-USER 20 > (pop c1)
1
also:
CL-USER 6 > '#1=(1 2 3 . #1#)
#1=(1 2 3 . #1#)
With a bit of CLOS added:
(defclass circular ()
((items :initarg :items)))
(defmethod initialize-instance :after ((c circular) &rest initargs)
(setf (slot-value c 'items) (circular (slot-value c 'items))))
(defmethod next-item ((c circular))
(prog1 (first (slot-value c 'items))
(setf (slot-value c 'items)
(rest (slot-value c 'items)))))
CL-USER 7 > (setf circ1 (make-instance 'circular :items (list 1 2 3)))
#<CIRCULAR 40200017CB>
CL-USER 8 > (next-item circ1)
1
CL-USER 9 > (next-item circ1)
2
CL-USER 10 > (next-item circ1)
3
CL-USER 11 > (next-item circ1)
1
CL-USER 12 > (next-item circ1)
2
In Sharpsign Equal-Sign notation, it's written as #0=(1 2 3 . #0#).
Here's a function which creates such a list from the given arguments:
(defun circular (first &rest rest)
(let ((items (cons first rest)))
(setf (cdr (last items)) items)))
Then, calling (circular 1 2 3) will return the circular list you wanted. Just use car and cdr to iterate through the elements ad infinitum.
And if you really want an iterator function that takes no arguments and returns the next item for each call, here's how you might do it:
(defun make-iter (list)
(lambda ()
(pop list)))
First, you want to let the printer know to recognize circular lists instead of trying to print the whole list:
(setf *print-circle* t)
Next, you can create a circular list using the Sharpsign Equal-Sign notation:
(setq x '#1=(1 2 3 . #1#))
Here is an idea worked out for a circular list in Lisp.
;;; Showing structure of the list
;;; (next prev is-end val)
; create items
setf L-0 (L-1 L-3 t "L-0 sentry") ; this will be the sentry item so know where to stop
setf L-1 (L-2 L-0 nil "L-1")
setf L-2 (L-3 L-1 nil "L-2")
setf L-3 (L-0 L-2 nil "L-3")
; how to access L-2 from L-0
eval (first (eval (first L-0)))
; result: (L-3 L-1 NIL "L-2")
I'm not giving defun functions to make adding, removing, and accessing the items. I'm thinking that what I gave is enough to show what you need to do in any functions you define for this kind of circular list. This appeared to me to work in the Listener.