Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Q:reference values

6 views
Skip to first unread message

CMSC 420

unread,
Mar 14, 1996, 3:00:00 AM3/14/96
to
I'm writing my first LISP program. I understand that function arguments
are generally local variables, such as

(defun sum (x y z) (setq z (+ x y)))

Normally, the summed value is the return value. Is it possible to keep
the summed value in z? In C, one would use a reference, such as

void sum (int x, int y, int& z) { z = x + y; }

I know I could do this by making z global and not putting z in the
argument list, but I don't want to.

dcwhite

unread,
Mar 14, 1996, 3:00:00 AM3/14/96
to
In article <4ia0qs$k...@hecate.umd.edu>, bs...@csc.umd.edu

Put z in the argument list of the function that calls "sum".

dcw...@phoenix.net

Barry Margolin

unread,
Mar 15, 1996, 3:00:00 AM3/15/96
to
In article <4ia0qs$k...@hecate.umd.edu>, CMSC 420 <bs...@csc.umd.edu> wrote:
>I'm writing my first LISP program. I understand that function arguments
>are generally local variables, such as
>
>(defun sum (x y z) (setq z (+ x y)))
>
>Normally, the summed value is the return value. Is it possible to keep
>the summed value in z?

You'll have to write a macro:

(defmacro sum (x y z)
`(setq ,z (+ ,x ,y)))

Why do you need to do this? What's so hard about

(setq z (sum x y))

If you need to set multiple output variables, you can use
MULTIPLE-VALUE-BIND or MULTIPLE-VALUE-SETQ.

> In C, one would use a reference, such as
>
>void sum (int x, int y, int& z) { z = x + y; }

C doesn't have reference variables. That looks like C++ to me.

The reason C++ needs this feature is because structures and classes are
passed by copying. Thus, in order to update a member of an object that's
passed, you need to use either a pointer or a reference. References were
created to avoid frequent use of pointers.

Since Lisp doesn't copy objects when passing them, this is not necessary.
If you receive a structured object (e.g. a cons, array, defstruct, or CLOS
instance) as a parameter and update its contents, that change is seen by
all other references to the object.
--
Barry Margolin
BBN PlaNET Corporation, Cambridge, MA
bar...@bbnplanet.com
Phone (617) 873-3126 - Fax (617) 873-6351

Erik Naggum

unread,
Mar 15, 1996, 3:00:00 AM3/15/96
to
[CMSC 420]

| I'm writing my first LISP program. I understand that function
| arguments are generally local variables, such as
|
| (defun sum (x y z) (setq z (+ x y)))
|
| Normally, the summed value is the return value. Is it possible to keep

| the summed value in z? In C, one would use a reference, such as


|
| void sum (int x, int y, int& z) { z = x + y; }
|

| I know I could do this by making z global and not putting z in the
| argument list, but I don't want to.

references are necessary in a language that supports only one return value
from functions, but their existence has certainly allowed a new breed of
abuse of language constructs.

references in C++ (not C) introduce "in out" arguments, if I can borrow
terminology from Ada, except that an Ada system can implement them by
making the assignments in the caller, which is clean. references in C++
wreak havoc with the argument evaluation process, and requires that the
compiler treat each function uniquely. in Lisp, you have only two kinds:
either all the arguments are evaluated when called, or none.

I think the way you use this feature in C++ is a clear example of abuse.

1. special variables

in Lisp, you have special variables, which can cause one function's
variables to be modified by another, but these are by name.

(defun caller ()
(let ((z 0))
(declare (special z))
(sum 1 2)
z))

(defun sum (x y)
(declare (special z))


(setq z (+ x y)))

(caller) now evaluates to 3.

if you have (defvar z 0), (caller) still evaluates to 3, but the global z
is unchanged. if you call (sum 1 2) directly, the global z is changed.

2. macros

being able to call a function to write to a random variable is nice, but we
don't do that in Lisp. instead, when there is a need to write to a place,
we use generalized setter functions via `setf'. there already exists a
macro to increment a generalized place, `incf'. you could write `sumf':

(defmacro sumf (place &rest operands)
`(setf ,place (+ ,@operands)))

this will work for lexical variables, as well. it also allows such forms
as

(sumf (aref array 3 2 4) 1 1 2 3 5 8)

which will set the value of the array element [3,2,4] to the sum of the six
first Fibonacci numbers.

now, this is not a good use for the macro facility, IMNSHO, even in an
interpreted language.

also note that functions are generally not "void" in Lisp. if you insist,
you can use the final form (values) which indicates zero return values.

#<Erik>
--
the Internet made me do it

Carl L. Gay

unread,
Mar 16, 1996, 3:00:00 AM3/16/96
to

From: bs...@csc.umd.edu (CMSC 420)
Newsgroups: comp.lang.lisp
Date: 14 Mar 1996 20:50:36 GMT

I'm writing my first LISP program. I understand that function arguments
are generally local variables, such as

(defun sum (x y z) (setq z (+ x y)))

Normally, the summed value is the return value. Is it possible to keep
the summed value in z?

No, not if z is a parameter to the function. Or rather "yes, but only
until SUM returns."

In C, one would use a reference, such as

void sum (int x, int y, int& z) { z = x + y; }

I think you mean C++. And even there I wouldn't use a reference, but
that is a matter of style, I guess.

I know I could do this by making z global and not putting z in the
argument list, but I don't want to.

No! That would be uncivilized. :) Just use the return value. This
is just something you'll have to get used to if you want to use CL.

When you're comfortable with the basics of the language, look into
multiple values and macros, which are what CL uses instead of call by
reference.

-Carl

Boaz Chow

unread,
Mar 19, 1996, 3:00:00 AM3/19/96
to
I am new to lisp too. from what I have learned so far.

Everything in Lisp is function.
So, everything in Lisp has value.
The last (quote from my teacher) value of a function will be the value from
the last argument of the function. I am not sure what she was talking
about though.

So... I think your program should look better like this :

(defun sum (x y)
(+ x y)
)

(setq z sum(x y))





On Mar 14, 1996 20:50:36 in article <Q:reference values>, 'bs...@csc.umd.edu

(CMSC 420)' wrote:


>I'm writing my first LISP program. I understand that function arguments
>are generally local variables, such as
>
>(defun sum (x y z) (setq z (+ x y)))
>
>Normally, the summed value is the return value. Is it possible to keep
>the summed value in z? In C, one would use a reference, such as
>
>void sum (int x, int y, int& z) { z = x + y; }
>
>I know I could do this by making z global and not putting z in the
>argument list, but I don't want to.
--
______ Meow
\ OO / _/
:(__ =)
U \\
http://www.sci.csupomona.edu/~cchow

0 new messages