;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; This file is part of ICCLE2. ; ; ICCLE2 is free software: you can redistribute it and/or modify ; it under the terms of the GNU General Public License as published by ; the Free Software Foundation, either version 3 of the License, or ; (at your option) any later version. ; ; ICCLE2 is distributed in the hope that it will be useful, ; but WITHOUT ANY WARRANTY; without even the implied warranty of ; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ; GNU General Public License for more details. ; ; You should have received a copy of the GNU General Public License ; along with ICCLE2. If not, see . ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;

Median of a List of Numbers

;

General comments for those who tried the 'median' question ;

    ;
  1. Remember to keep local variables local (use let) ;
  2. Remember that the list has to be sorted before you look for ;medians, etc ;
;

Main Driver

;

There's two cases (odd and even numbered size lists): so let us do the common stuff in ; the main function and handle the quirks in sub-routines.

(defun median (l)
   (let* ((size     (length l))
	   (index50 (floor (* size 0.5))))
	   (l1      (ordered l)))
     (if (oddp size)
	 (median-odd  l1 index50)
	 (median-even l1 index50))))
;

Two cases

Case one:

(defun median-odd (l index50)
   (elt l index50))
;

Case two:

(defun median-even (l index50)
   (avg (elt l (1- index50))
	(elt l index50)))
;

Helper Functions

;

The following function shows my standard sort idioms:

(defun ordered (l &key (predicate #'<) (key #'identity))
   (stable-sort (copy-list l) predicate :key key))
;

And the following is almost too small to code as a sub-routine.

(defun avg (x y)
   (float (/ (+ x y) 2))
;