list.ss
#lang scheme/base
;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; BASE.plt - common routines that are shared by all other bzlib modules
;;
;; in a way, base.plt is the most fundamental module of the whole bzlib stack
;; and as such it also is the lowest level code.  We are not likely to
;; fix the code any time soon, and hence any of the functions here are
;; explicitly likely to be obsoleted or moved elsewhere.
;;
;; Proceed with caution.
;;
;;
;; Bonzai Lab, LLC.  All rights reserved.
;;
;; Licensed under LGPL.
;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;; list.ss - basic functionalities that has to do with list processing.
;; yc 9/8/2009 - first version

(require "base.ss")

(define (assoc/cdr key alist (default #f))
  (if-it (assoc key alist)
         (cdr it)
         default))

(define (assoc/s key alist (default '()))
  (let ((it (filter (lambda (kv)
                      (equal? (car kv) key))
                    alist)))
    (if (null? it) default it)))

;; this function is a combo of member & assoc
;; it's useful when we have a malformed alist, where when the
;; pair has no value, the key is retained
;; (or when there is no key, the value is retained)
(define (assoc* key lst (default #f))
  (define (helper rest)
    (cond ((null? rest) default)
          ;; assoc behavior
          ((and (pair? (car rest))
                (equal? key (caar rest)))
           (car rest))
          ;; member behavior
          ((and (not (pair? (car rest)))
                (equal? key (car rest)))
           rest)
          (else
           (helper (cdr rest)))))
  ;; (trace helper)
  (helper lst))

(define (assoc*/cdr key lst (default #f))
  (if-it (assoc* key lst)
         (cdr it)
         default))

(provide/contract 
 (assoc/cdr (->* (any/c list?)
                 (any/c)
                 any))
 (assoc/s (->* (any/c list?)
               (any/c)
               any))
 (assoc* (->* (any/c list?)
              (any/c)
              any))
 (assoc*/cdr (->* (any/c list?)
                  (any/c)
                  any))
 )