;;;
;;; CPACKAGES: Count the number of symbols in the packages
;;;
;;; ----------------------------------------------------------------------
;;;
;;; This file is part of ILOG Talk.
;;; Inquiries to ILOG S.A.
;;;              9 rue de Verdun, BP 85,
;;;              94253 Gentilly Cedex, France.
;;;
;;; Copyright (c) 1995-1996 by ILOG
;;; ----------------------------------------------------------------------
;;;

(defun cpackages ()
  ;; returns an Alist ((pack . count) ... (pack . count))
  (let ((al (list (cons () 0)))
        (tot 0))
    (map-symbols
     (lambda (symb)
       (incf tot)
       (.count-package (id-package symb) al)))
    (for ((slot in: (nlsort al #'.pack<)))
      (printf "%-20A%4d  %3d%%\n"
	      (car slot) (cdr slot)
	      (int (/ (* (cdr slot) 100.) tot))))))

(defun .pack<  (x y)
  (if (eq (cdr x) (cdr y))
      (.pack-comp (car x) (car y))
    (i> (cdr x) (cdr y))))

(defun .count-package (pack al)
  (let ((slot (assoc pack al)))
     (if (consp slot)
	 (setf (cdr slot) (i1+ (cdr slot)))
       (nappend1f al (cons pack 1)))))

(defun .pack-comp (a b)
  ;; Compare 2 symbols by considering that their packages form part of
  ;; their name.
  ;; compare 2 symboles en conside'rant que
  ;; les packages font partie du nom.
  ;; Si non symbole: place' devant.
  (if (eq (id-package a) (id-package b))
      (string< (id-name a) (id-name b))
    (let ((pa (id-package a)))
      (or (not (symbolp pa))
	  (let ((pb (id-package b)))
	    (and (symbolp pb)
		 (.pack-comp pa pb)))))))
		
