Lisp - List of lists with variable size - lisp

I have to represent a board game using lisp. To do that i have to create a function that builds the board.
This function receives an integer that represents the number of sublist the original list as to have. each one of this sublists have a different size growing in 3*n proportion.
As an example ifthe function is called with the number 3, it will create a list with 3 sublists, the first with 3 position, the second with six and the third with 9.
Also, each of the positions need to be initialized with ´*.
To do this i think i have to make a recursive call to make-list, but i can't seem to do that right. i'be tried to use the 'dotimes' cycle to do that, but i didn't have any sucess with that.
So far i have:
(defun faz-tabuleiro (n_aneis)
(make-list n_aneis :initial-element (...)
Wich creates the main list, but how can i represent the sublists inside with the right size?

Does this do what you want?
(defun make-table (n)
(loop :for i :from 1 :to n
:collect (make-list (* i 3) :initial-element "*")))

Map over a list of numbers being the length of the sublists. Use a function for this mapping which returns the right list initialized with the initial element.

Related

Attempting to define a function that provides the minimum integer in a list of numbers SPECIFICALLY using do loops (not do* or dolist, etc.)

I have an assignment for class specifically testing our understanding of do, asking to define a function to produce the minimum of a list of numbers. We are asked to also use a secondary function ("smaller") to do so.
I have no previous experience coding, and am forced to stay within the boundaries of do; I've been reading up on the issue as much as I can, but almost everything I find just suggests using other methods (do*, COND, etc.).
I defined a simple "smaller" as:
(defun smaller (x y)
(if (< x y) x y))
I then approached the problem as such:
(defun minimum (lst)
"(lst)
Returns the minimum of a list of numbers."
(do ((numbers lst (cdr numbers))
(min (car numbers) (smaller min (cadr numbers))))
((null numbers) min)))
I feel there's an issue where the "smaller" function can't be applied on the first loop (feedback about this would be great), otherwise my immediate issue is getting an error of: "UNBOUND-VARIABLE" for the variable "NUMBERS". I am not sure which 'area' is causing the confusion: if I have poorly formatted the do loop entirely, or if one of the second/third/etc. "numbers" is causing an issue.
Can someone provide some feedback? -- again keeping in mind that we are limited specifically to simple do loops, and that I definitely don't have a perfect understanding of what I've already got down.
Thanks so much in advance.
Do binds in parallel, so numbers is not bound when min is first bound. You could fix that by using (car lst) instead of (car numbers) there.
You need to fix the end condition then: (cadr numbers) is nil on the last iteration, you need to stop before that.
For better readability, I'd suggest to use first and second instead of car and cadr here.
You could still refer to numbers as long as you used do*, which is a sequentially binding variant of do. Then you'd have to use car instead of cadr - you're now picking the first number from an already reduced list. And you'd need to modify your end condition to avoid calling smaller with a NIL argument - you should be able to figure this out easily.

how to find element of list by knowing its position in clisp?

If I know the position of an element in a list in clisp, then how could I retrieve the element knowing its position. Is there any predefined function for it?
For lists only there is NTH:
CL-USER> (nth 2 '(1 2 3 4 5))
3
For SEQUENCES (vectors, strings, lists ...) there is ELT:
CL-USER> (elt '(1 2 3 4 5) 2)
3
If you really need a lot to access element by index, I'll advice you to consider using vectors (and access elements by aref) instead of lists, especially if you have logn sequences, because accessing element by index in lists may need to travel along all list to your element.
Of course, if you have small amount of data, you wan't feel any difference, but it looks good to use things right for me.
I depends on your lisp flavour. The best thing is to just write a 2 parameter function which returns a list-item. Parameter 1 item_index, param 2 the list, just recursively reduce index as you move through and return the 0th of 1st index. Note you need to decide if the car of a list is index 1 or index 0. Humans prefer one,computers 0.

How to define a function that returns half of input, in two different ways?

I am reading a Gentle Introduction to Symbolic Computation and it asks this question. Basically, the previous content deals with making up bigger functions with small ones. (Like 2- will be made of two 1- (decrement operators for lisp))
So one of the questions is what are the two different ways to define a function HALF which returns one half of its input. I have been able to come up with the obvious one (dividing number by 2) but then get stuck. I was thinking of subtracting HALF of the number from itself to get half but then the first half also has to be calculated...(I don't think the author intended to introduce recursion so soon in the book, so I am most probably wrong).
So my question is what is the other way? And are there only two ways?
EDIT : Example HALF(5) gives 2.5
P.S - the book deals with teaching LISP of which I know nothing about but apparently has a specific bent towards using smaller blocks to build bigger ones, so please try to answer using that approach.
P.P.S - I found this so far, but it is on a completely different topic - How to define that float is half of the number?
Pdf of book available here - http://www.cs.cmu.edu/~dst/LispBook/book.pdf (ctrl+f "two different ways")
It's seems to be you are describing peano arithmetic. In practice it works the same way as doing computation with fluids using cups and buckets.
You add by taking cups from the source(s) to a target bucket until the source(s) is empty. Multiplication and division is just advanced adding and substraction. To halve you take from source to two buckets in alterations until the source is empty. Of course this will either do ceil or floor depending on what bucket you choose to use as answer.
(defun halve (x)
;; make an auxillary procedure to do the job
(labels ((loop (x even acc)
(if (zerop x)
(if even (+ acc 0.5) acc)
(loop (- x 1) (not even) (if even (+ acc 1) acc)))))
;; use the auxillary procedure
(loop x nil 0)))
Originally i provided a Scheme version (since you just tagged lisp)
(define (halve x)
(let loop ((x x) (even #f) (acc 0))
(if (zero? x)
(if even (+ acc 0.5) acc)
(loop (- x 1) (not even) (if even (+ acc 1) acc)))))
Edit: Okay, lets see if I can describe this step by step. I'll break the function into multiple lines also.
(defun half (n)
;Takes integer n, returns half of n
(+
(ash n -1) ;Line A
(if (= (mod n 2) 1) .5 0))) ;Line B
So this whole function is an addition problem. It is simply adding two numbers, but to calculate the values of those two numbers requires additional function calls within the "+" function.
Line A: This performs a bit-shift on n. The -1 tells the function to shift n to the right one bit. To explain this we'll have to look at bit strings.
Suppose we have the number 8, represented in binary. Then we shift it one to the right.
1000| --> 100|0
The vertical bar is the end of the number. When we shift one to the right, the rightmost bit pops off and is not part of the number, leaving us with 100. This is the binary for 4.
We get the same value, however if we perform the shift on nine:
1001| --> 100|1
Once, again we get the value 4. We can see from this example that bit-shifting truncates the value and we need some way to account for the lost .5 on odd numbers, which is where Line B comes in.
Line B: First this line tests to see if n is even or odd. It does this by using the modulus operation, which returns the remainder of a division problem. In our case, the function call is (mod n 2), which returns the remainder of n divided by 2. If n is even, this will return 0, if it is odd, it will return 1.
Something that might be tripping you up is the lisp "=" function. It takes a conditional as its first parameter. The next parameter is the value the "=" function returns if the conditional is true, and the final parameter is what to return if the conditional is false.
So, in this case, we test to see if (mod n 2) is equal to one, which means we are testing to see if n is odd. If it is odd, we add .5 to our value from Line A, if it is not odd, we add nothing (0) to our value from Line A.

Problems with Nth in common lisp

I'm trying to write a function that can calculate GPA. Now I can do limited calculation(only 3 ),but I stuck on how to calculate more , without using loop or recursion (that's the requirement of subject) how to expend nth function? like: (nth n) ,if so ,is that mean i need to write a lambda expression? As an newbie, I maynot describe the question clearly, really need some help..
Glist is grade points Clist is credit hours.
GPA=( gradepoint *credithour + gradepoint *credithour) / ( the sum of credithour) like: (3*1+3*2+4*1)/(1+2+1)
here is my code:
(defun gpa (Glist Clist)
(format t "~3,2f~%"
(/
(+(nth 0 (mapcar #' * Glist Clist))
(nth 1 (mapcar #' * Glist Clist))
(nth 2 (mapcar #' * Glist Clist)))
(+ (nth 0 Clist)
(nth 1 Clist)
(nth 2 Clist))
);end "/"
);end "format"
(values) );end
EDIT
This seems like a good opportunity to emphasize some common (little c) Lisp ideas, so I fleshed out my answer to illustrate.
As mentioned in another answer, you could use a sum function that operates on lists (of numbers):
(defun sum (nums)
(reduce #'+ nums))
The dot product is the multiplicative sum of two (equal-length) vectors:
(defun dot-product (x y)
(sum (mapcar #'* x y)))
The function gpa is a simple combination of the two:
(defun gpa (grades credits)
(/ (dot-product grades credits) (sum credits)))
The example from the question results in the answer we expect (minus being formatted as a float):
(gpa '(3 3 4) '(1 2 1))
> 13/4
There are a few things worth mentioning from this example:
You should learn about map, reduce, and their variants and relatives. These functions are very important to Lisp and are very useful for operating on lists. map* functions generally map sequences to a sequence, and reduce usually transforms a sequence into to a single value (you can however use forms like (reduce #'cons '(1 2 3))).
This is a good example of the "bottom-up" approach to programming; by programming simple functions like sum that are often useful, you make it easy to write dot-product on top of it. Now the gpa function is a simple, readable function built on top of the other two. These are all one-liners, and all are easily readable to anyone who has a basic knowledge of CL. This is in contrast to the methodology usually applied to OOP.
There is no repetition of code. Sure, sum is used more than once, but only where it makes sense. You can do very little more to abstract the notion of a sum of the elements of a list. It's more natural in Scheme to write functions with functions, and that's a whole different topic. This is a simple example, but no two functions are doing the same thing.
If you're using nth to traverse a list, you're doing it wrong. In this case, you might want to write a summing function:
(defun sum (items)
(reduce #'+ items))

extract/slice/reorder lists in (emacs) lisp?

In python, you might do something like
i = (0, 3, 2)
x = [x+1 for x in range(0,5)]
operator.itemgetter(*i)(x)
to get (1, 4, 3).
In (emacs) lisp, I wrote this function called extract which does something similar,
(defun extract (elems seq)
(mapcar (lambda (x) (nth x seq)) elems))
(extract '(0 3 2) (number-sequence 1 5))
but I feel like there should be something built in? All I know is first, last, rest, nth, car, cdr... What's the way to go? ~ Thanks in advance ~
If your problem is the speed then use (vector 1 2 3 4 5) instead of a list, and (aref vec index) to get the element.
(defun extract (elems seq)
(let ((av (vconcat seq)))
(mapcar (lambda (x) (aref av x)) elems)))
If you're going to extract from the same sequence many times of course it make sense to store the sequence in a vector just once.
Python lists are indeed one-dimensional arrays, the equivalent in LISP are vectors.
I've only done simple scripting in elisp, but it's a relatively small language. And extract is a very inefficient function on linked lists, which is the default data structure in emacs lisp. So it's unlikely to be built-in.
Your solution is the best straightforward one. It's n^2, but to make it faster requires a lot more code.
Below is a guess at how it might work, but it might also be totally off base:
sort elems (n log n)
create a map that maps elements in sorted elem to their indices in original elem (probably n log n, maybe n)
iterate through seq and sorted elem. Keep only the indices in sorted elem (probably n, maybe n log n, depending on whether it's a hash map or a tree map)
sort the result by the values of the elem mapping (n log n)
From My Lisp Experiences and the Development of GNU Emacs:
There were people in those days, in 1985, who had one-megabyte machines without virtual memory. They wanted to be able to use GNU Emacs. This meant I had to keep the program as small as possible.
For instance, at the time the only looping construct was ‘while’, which was extremely simple. There was no way to break out of the ‘while’ statement, you just had to do a catch and a throw, or test a variable that ran the loop. That shows how far I was pushing to keep things small. We didn't have ‘caar’ and ‘cadr’ and so on; “squeeze out everything possible” was the spirit of GNU Emacs, the spirit of Emacs Lisp, from the beginning.
Obviously, machines are bigger now, and we don't do it that way anymore. We put in ‘caar’ and ‘cadr’ and so on, and we might put in another looping construct one of these days.
So my guess is, if you don't see it, it's not there.