Hello,
Perhaps my previous message was too verbose, or there is someone still trying it out. After working on it some more, my question boils down to this:
How the heck do I use read-line in a program?
Take the following REPL session as an example:
Gambit v4.2.6
(read)
"This is an s-expression" ;<=typed "This is an s-expression" ;<=echoed
(read-line)
""
(read-line)This is an s-expression
"This is an s-expression"
So, I know that I can call read-line from call-with-input-file, or call-with-input-string, but if I have an input file or a string, then I already have what I want. What I want is for the user to input a line of text, and for the program to do something with that line of text (as a string).
However I use (read-line), it always accepts the text that was already there (usually "" or "\t"). How do I get it (or some other procedure) to accept user input? What would I put into (call-with-input-string ... read-line)? I've tried a few things, and I always just end up redefining read-line:
(define (read-this)
(let ((input (read-char)) (output "")) (if (char=? input #\newline) output (string-append (string input) (read-this)))))
(read-this)
""
(read-this)this is text, baby
"this is text, baby"
I'm really not getting this; can someone please explain it to me?
Thanks, Joel
Afficher les réponses par date
On 24-Apr-08, at 10:47 AM, Joel J. Adamson wrote:
How the heck do I use read-line in a program?
Take the following REPL session as an example:
Gambit v4.2.6
(read)
"This is an s-expression" ;<=typed "This is an s-expression" ;<=echoed
(read-line)
""
(read-line)This is an s-expression
"This is an s-expression"
So, I know that I can call read-line from call-with-input-file, or call-with-input-string, but if I have an input file or a string, then I already have what I want. What I want is for the user to input a line of text, and for the program to do something with that line of text (as a string).
However I use (read-line), it always accepts the text that was already there (usually "" or "\t"). How do I get it (or some other procedure) to accept user input? What would I put into (call-with-input-string ... read-line)? I've tried a few things, and I always just end up redefining read-line:
(define (read-this)
(let ((input (read-char)) (output "")) (if (char=? input #\newline) output (string-append (string input) (read-this)))))
(read-this)
""
(read-this)this is text, baby
"this is text, baby"
I'm really not getting this; can someone please explain it to me?
I don't understand the problem you are having! Your read-this is behaving exactly like read-line !
Marc
Marc Feeley feeley@iro.umontreal.ca writes:
On 24-Apr-08, at 10:47 AM, Joel J. Adamson wrote:
How the heck do I use read-line in a program?
[...]
and I always just end up redefining read-line:
(define (read-this)
(let ((input (read-char)) (output "")) (if (char=? input #\newline) output (string-append (string input) (read-this)))))
(read-this)
""
(read-this)this is text, baby
"this is text, baby"
I'm really not getting this; can someone please explain it to me?
I don't understand the problem you are having! Your read-this is behaving exactly like read-line !
Yeah, it's the same. I was saying my frustration --- and this is monumental because it's the only major frustration I've had in two years of working with Scheme --- was that all I could come up with was a re-implementation of read-line.
The problem is really that I want read-line to behave exactly like (read) except for the form in which it accepts the input: wait for input and accept that input as a string. I could have the user input a line in double-quotes and just use (read), but I would prefer the user not to type the quote marks. Am I being too picky...? The other problem with using a recursive reading-by-token procedure is that the user then has to use ^D to end the line (I've reserved ^D to exit the program).
Joel
On 24-Apr-08, at 12:24 PM, Joel J. Adamson wrote:
Marc Feeley feeley@iro.umontreal.ca writes:
On 24-Apr-08, at 10:47 AM, Joel J. Adamson wrote:
How the heck do I use read-line in a program?
[...]
and I always just end up redefining read-line:
(define (read-this)
(let ((input (read-char)) (output "")) (if (char=? input #\newline) output (string-append (string input) (read-this)))))
(read-this)
""
(read-this)this is text, baby
"this is text, baby"
I'm really not getting this; can someone please explain it to me?
I don't understand the problem you are having! Your read-this is behaving exactly like read-line !
Yeah, it's the same. I was saying my frustration --- and this is monumental because it's the only major frustration I've had in two years of working with Scheme --- was that all I could come up with was a re-implementation of read-line.
The problem is really that I want read-line to behave exactly like (read) except for the form in which it accepts the input: wait for input and accept that input as a string. I could have the user input a line in double-quotes and just use (read), but I would prefer the user not to type the quote marks. Am I being too picky...? The other problem with using a recursive reading-by-token procedure is that the user then has to use ^D to end the line (I've reserved ^D to exit the program).
Joel
I think I now understand your problem... you want to flush the input buffers so that the call to read-line will return only what was typed by the user after the moment of the call. So here's one way to do it:
(define (flush-input port) (input-port-timeout-set! port 0.001) (let loop () (if (not (eof-object? (read-line port))) (loop))) (input-port-timeout-set! port +inf.0))
(define (read-line-from-console) (let ((port (console-port))) (flush-input port) (read-line port)))
(pp (read-line-from-console)) (pp (read-line-from-console)) (pp (read-line-from-console)) (pp (read-line-from-console))
Marc Feeley feeley@iro.umontreal.ca writes:
On 24-Apr-08, at 12:24 PM, Joel J. Adamson wrote:
Marc Feeley feeley@iro.umontreal.ca writes:
On 24-Apr-08, at 10:47 AM, Joel J. Adamson wrote:
How the heck do I use read-line in a program?
[...]
and I always just end up redefining read-line:
(define (read-this)
(let ((input (read-char)) (output "")) (if (char=? input #\newline) output (string-append (string input) (read-this)))))
(read-this)
""
(read-this)this is text, baby
"this is text, baby"
I'm really not getting this; can someone please explain it to me?
I don't understand the problem you are having! Your read-this is behaving exactly like read-line !
I think I now understand your problem... you want to flush the input buffers so that the call to read-line will return only what was typed by the user after the moment of the call. So here's one way to do it:
(define (flush-input port) (input-port-timeout-set! port 0.001) (let loop () (if (not (eof-object? (read-line port))) (loop))) (input-port-timeout-set! port +inf.0))
I see; it had not occurred to me to directly stall the port. On top of that...
(define (read-line-from-console) (let ((port (console-port))) (flush-input port) (read-line port)))
I was unaware of console-port! I was trying to find if there was a "stdin-port" or "tty-port;" I guess (console-port) should have been my next guess.
(pp (read-line-from-console))
Excellent, that is exactly what I was going for.
Thank you! Joel