Reading in Integers to a list

Discussion of Common Lisp
Mercfh
Posts: 17
Joined: Tue Mar 30, 2010 3:39 pm
Location: Miami,FL

Reading in Integers to a list

Post by Mercfh » Mon Apr 05, 2010 11:46 pm

Simple question which sadly I cannot find an answer to. Basically Im finishing up my ternary tree Program (it was in another thread) but I Have the Insert/ and print functions done.
problem is is that I need to read in integers into a list before I run the insert/print function on them.

Anyways Before I was using an example list.

Code: Select all

(defparameter *MYLIST*
(list 4 6 4 18 8 2 14 7 15 5 19 12 15 5 9 0 17 2 2 19))
But I need to make it where I read in the numbers, like ask the user for numbers until they hit N or something to stop. then put them into a list. and then run the insert/print function as I read in each value.

So it'd be something like this:
Read In value---> 5 (user inputs value)
Run Insert/then print on that
Read in value.....
Run Insert/print
Read In value
etc...

And go on until I stop inputting numbers.

Code: Select all

(defun T-tree()
(let ((test nil))
(dolist (run *MYLIST*)
(insert test run)
(print (print-tree)))
Right now this Goes through the "example" list I have (named MYLIST) and goes through each Value and does it.
but I want it to do the insert function and print function as the values come in. So first it does it with 1 value.....then with 2 values......etc

I figured the test function should be the same. but I just have some kinda function that asks for another Integer for the list, and then adds it to it.
So something like this?

Code: Select all

(defun T-tree()
(let ((test nil))
(askuser) #Ask for Next integer to be put into *MYLIST*
(dolist (run *MYLIST*)
(insert test run)
(print (print-tree)))
Ideas? Criticism? Comments?

thanks a bunch

nuntius
Posts: 538
Joined: Sat Aug 09, 2008 10:44 am
Location: Newton, MA

Re: Reading in Integers to a list

Post by nuntius » Tue Apr 06, 2010 4:52 am

Here's a sample input loop.

Code: Select all

(do (value)
    (nil)
  (setf value (read-from-string (read-line) nil nil))
  (unless value (return))
  (format t "You entered ~A~%" value))

Jasper
Posts: 209
Joined: Fri Oct 10, 2008 8:22 am
Location: Eindhoven, The Netherlands
Contact:

Re: Reading in Integers to a list

Post by Jasper » Tue Apr 06, 2010 4:59 am

Note that the *standard-input* stream is defaultly the user input. You can make any character stream get input from that.

You could enter the collector made by nconcing into the following:

Code: Select all

(defun callback-read (from callback &key (stop (gensym)))
  "Reading, where each expression is put into a callback."
  (typecase from
    (string
     (with-open-file (stream from) (list-read stream :stop stop)))
    (stream
     (do ((read (read from nil stop) (read from nil stop)))
         ((eql read stop) (values))
       (funcall callback read)))))
And then input the stream *standard-input*.

gugamilare
Posts: 406
Joined: Sat Mar 07, 2009 6:17 pm
Location: Brazil
Contact:

Re: Reading in Integers to a list

Post by gugamilare » Tue Apr 06, 2010 5:45 am

I believe that the simplest and prettiest function that asks for values is this:

Code: Select all

(defun prompt (string)
  (format t "~A: " string)
  (read))

Code: Select all

cl-user> (prompt "Enter an integer")
Enter an integer: 2
2
A more elaborate version:

Code: Select all

(defun prompt (string &key (output *standard-output*) (input *standard-input*))
  (format output "~A: " string)
  (read input))

Mercfh
Posts: 17
Joined: Tue Mar 30, 2010 3:39 pm
Location: Miami,FL

Re: Reading in Integers to a list

Post by Mercfh » Tue Apr 06, 2010 11:30 am

Well Is there any way to read these into a list? (like add them)

say User enters 5
the list is [5]
I do my functions/insert/etc
Next the user enters 7
the list is now [5 7]
do functions/insert etc/

and so on..

gugamilare
Posts: 406
Joined: Sat Mar 07, 2009 6:17 pm
Location: Brazil
Contact:

Re: Reading in Integers to a list

Post by gugamilare » Tue Apr 06, 2010 1:25 pm

You mean like this?

Code: Select all

cl-user> (loop for value = (prompt "Please enter an integer or \"end\" to finish:")
              until (eq value 'end)
              collect value)
Please enter an integer or "end" to finish:: 1
Please enter an integer or "end" to finish:: 2
Please enter an integer or "end" to finish:: 3
Please enter an integer or "end" to finish:: 4
Please enter an integer or "end" to finish:: 5
Please enter an integer or "end" to finish:: 6
Please enter an integer or "end" to finish:: end
(1 2 3 4 5 6)

Mercfh
Posts: 17
Joined: Tue Mar 30, 2010 3:39 pm
Location: Miami,FL

Re: Reading in Integers to a list

Post by Mercfh » Tue Apr 06, 2010 2:58 pm

gugamilare wrote:You mean like this?

Code: Select all

cl-user> (loop for value = (prompt "Please enter an integer or \"end\" to finish:")
              until (eq value 'end)
              collect value)
Please enter an integer or "end" to finish:: 1
Please enter an integer or "end" to finish:: 2
Please enter an integer or "end" to finish:: 3
Please enter an integer or "end" to finish:: 4
Please enter an integer or "end" to finish:: 5
Please enter an integer or "end" to finish:: 6
Please enter an integer or "end" to finish:: end
(1 2 3 4 5 6)
\

Yes something like that.
But what variable is the list? is it collect? or wut.
(like if I wanted to use the list in the "dolist" function)

gugamilare
Posts: 406
Joined: Sat Mar 07, 2009 6:17 pm
Location: Brazil
Contact:

Re: Reading in Integers to a list

Post by gugamilare » Tue Apr 06, 2010 4:39 pm

Mercfh wrote:Yes something like that.
But what variable is the list? is it collect? or wut.
(like if I wanted to use the list in the "dolist" function)
The variable containing the list is hidden, its value is returned when the loop finishes. To use the list, you need to save it into a variables afterwards, e.g.:

Code: Select all

(let ((list (loop for value = (prompt "Please enter an integer or \"end\" to finish:")
                  until (eq value 'end)
                  collect value)))
  (format t "This is the list constructed: ~A~%" list)
  (format t "These are its elements:")
  (dolist (element list)
    (format t "~A" element))
  (format t "~%"))
Try evaluating that code.

Mercfh
Posts: 17
Joined: Tue Mar 30, 2010 3:39 pm
Location: Miami,FL

Re: Reading in Integers to a list

Post by Mercfh » Tue Apr 06, 2010 4:51 pm

Ok So it's saved into the variable list "element" there im assuming? or is the list variable actually called list (sorry this is my first time with lisp lol.....can u tell haha)?


Either way could I make this into a function that I could use in my function loop?

gugamilare
Posts: 406
Joined: Sat Mar 07, 2009 6:17 pm
Location: Brazil
Contact:

Re: Reading in Integers to a list

Post by gugamilare » Tue Apr 06, 2010 5:30 pm

Mercfh wrote:Ok So it's saved into the variable list "element" there im assuming? or is the list variable actually called list (sorry this is my first time with lisp lol.....can u tell haha)?
The list is actually called list. The variable element runs through the elements of the list, printing each one at a time.

The loop

Code: Select all

(loop for value = (prompt "Please enter an integer or \"end\" to finish:")
   until (eq value 'end)
   collect value)
will read your inputs and create a list. The list is then returned, and it will be lost unless you save it somewhere. let is what you use to create new variables. In this case, we created a variable named list and saved the result of the last form into it:

Code: Select all

(let ((list     ;; <- this is the variable created, its value will be the next form
       (loop for value = (prompt "Please enter an integer or \"end\" to finish:")
          until (eq value 'end)
          collect value)))
  ...)
dolist is used to iterate through the elements of the list, in this case we used it to print all the elements, one at a time.
Mercfh wrote:Either way could I make this into a function that I could use in my function loop?
This is easy, just define a function and put the loop above (the first code box in this post) inside.

Post Reply