[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

(typep <instance>)



    Date: Tue, 31 May 88 17:24 PDT
    From: Jerry@marlowe.inference.dialnet.symbolics.com (Jerry Bakin)

    An application I am involved with has a simple process wait function:
    It iterates over the elements of an array, and if the element is of the
    appropriate type (a session), that element is sent a :poll message.

    Because the elements of the array can be nil, a keyword, or an object;
    the iteration is driven off the results of (typep ....)

    While we were timing various portions of the System, we discovered
    thousands of conses of (INSTANCE SESSION) formed every second!

    We traced these conses to the call to typep!

    For instance, try the following:

    (defflavor ship () ())
    SHIP
      (setf s (make-instance 'ship))
    #<SHIP 10302715>
      (time (progn (typep s 'ship) (typep s 'ship)) t)
    Evaluation of (PROGN (TYPEP S #) (TYPEP S #)) took 0.001267 seconds of elapsed time
    including 0.000 seconds waiting for the disk for 0 faults.
    4 list words consed in WORKING-STORAGE-AREA.
    Consed in list region of WORKING-STORAGE-AREA:
    (INSTANCE SHIP)
    (INSTANCE SHIP)
    T

    These conses are actually created by a call to cli::type-expand.

    Now I imagine these conses will be caught by the ephemeral garbage
    collector, but I wonder if they are required at all!

    I am not looking for stop gap solutions; there are several ways of
    eliminating the call in this case.  I would like to see typep itself
    fixed or at the very least documented in this inefficiency.

    Jerry.

If the flavor is known about at the time the TYPEP form is compiled,
(TYPEP <thing> '<flavor-name>) is optimized into (SI:TYPEP-FLAVOR
<thing> '<flavor-name>), which doesn't cons.  The same thing is true for
DEFSTRUCT types.  Your examples above were interpreted, so they didn't
get optimized.  Try

(defun ship-p (s)
  (typep s 'ship))

(compile 'ship-p)

(time (progn (ship-p s) (ship-p s)) t)

In general, compiled TYPEP with a constant second argument seems to
produce good code.

I tried all the above in 7.2, but I'm pretty sure it did the same thing
in 7.1.

                                                barmar