0
|
1 ;;; assoc.el --- insert/delete/sort functions on association lists
|
|
2
|
2
|
3 ;; Copyright (C) 1996 Free Software Foundation, Inc.
|
|
4
|
0
|
5 ;; Author: Barry A. Warsaw <bwarsaw@cen.com>
|
|
6 ;; Keywords: extensions
|
|
7
|
2
|
8 ;; This file is part of XEmacs.
|
|
9
|
|
10 ;; XEmacs is free software; you can redistribute it and/or modify
|
|
11 ;; it under the terms of the GNU General Public License as published by
|
|
12 ;; the Free Software Foundation; either version 2, or (at your option)
|
|
13 ;; any later version.
|
0
|
14
|
2
|
15 ;; XEmacs is distributed in the hope that it will be useful, but
|
|
16 ;; WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
17 ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
18 ;; General Public License for more details.
|
0
|
19
|
2
|
20 ;; You should have received a copy of the GNU General Public License
|
|
21 ;; along with XEmacs; see the file COPYING. If not, write to the Free
|
|
22 ;; Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
|
|
23 ;; 02111-1307, USA.
|
|
24
|
|
25 ;;; Synched up with: FSF 19.34.
|
0
|
26
|
|
27 ;;; Commentary:
|
|
28
|
|
29 ;; Association list utilities providing insertion, deletion, sorting
|
|
30 ;; fetching off key-value pairs in association lists.
|
|
31
|
|
32 ;;; Code:
|
|
33
|
|
34 (defun asort (alist-symbol key)
|
|
35 "Move a specified key-value pair to the head of an alist.
|
|
36 The alist is referenced by ALIST-SYMBOL. Key-value pair to move to
|
|
37 head is one matching KEY. Returns the sorted list and doesn't affect
|
|
38 the order of any other key-value pair. Side effect sets alist to new
|
|
39 sorted list."
|
|
40 (set alist-symbol
|
|
41 (sort (copy-alist (eval alist-symbol))
|
|
42 (function (lambda (a b) (equal (car a) key))))))
|
|
43
|
|
44
|
|
45 (defun aelement (key value)
|
|
46 "Makes a list of a cons cell containing car of KEY and cdr of VALUE.
|
|
47 The returned list is suitable as an element of an alist."
|
|
48 (list (cons key value)))
|
|
49
|
|
50
|
|
51 (defun aheadsym (alist)
|
|
52 "Return the key symbol at the head of ALIST."
|
|
53 (car (car alist)))
|
|
54
|
|
55
|
|
56 (defun anot-head-p (alist key)
|
|
57 "Find out if a specified key-value pair is not at the head of an alist.
|
|
58 The alist to check is specified by ALIST and the key-value pair is the
|
|
59 one matching the supplied KEY. Returns nil if ALIST is nil, or if
|
|
60 key-value pair is at the head of the alist. Returns t if key-value
|
|
61 pair is not at the head of alist. ALIST is not altered."
|
|
62 (not (equal (aheadsym alist) key)))
|
|
63
|
|
64
|
|
65 (defun aput (alist-symbol key &optional value)
|
|
66 "Inserts a key-value pair into an alist.
|
|
67 The alist is referenced by ALIST-SYMBOL. The key-value pair is made
|
|
68 from KEY and optionally, VALUE. Returns the altered alist or nil if
|
|
69 ALIST is nil.
|
|
70
|
|
71 If the key-value pair referenced by KEY can be found in the alist, and
|
|
72 VALUE is supplied non-nil, then the value of KEY will be set to VALUE.
|
|
73 If VALUE is not supplied, or is nil, the key-value pair will not be
|
|
74 modified, but will be moved to the head of the alist. If the key-value
|
|
75 pair cannot be found in the alist, it will be inserted into the head
|
|
76 of the alist (with value nil if VALUE is nil or not supplied)."
|
|
77 (let ((elem (aelement key value))
|
|
78 alist)
|
|
79 (asort alist-symbol key)
|
|
80 (setq alist (eval alist-symbol))
|
|
81 (cond ((null alist) (set alist-symbol elem))
|
|
82 ((anot-head-p alist key) (set alist-symbol (nconc elem alist)))
|
|
83 (value (setcar alist (car elem)))
|
|
84 (t alist))))
|
|
85
|
|
86
|
|
87 (defun adelete (alist-symbol key)
|
|
88 "Delete a key-value pair from the alist.
|
|
89 Alist is referenced by ALIST-SYMBOL and the key-value pair to remove
|
|
90 is pair matching KEY. Returns the altered alist."
|
|
91 (asort alist-symbol key)
|
|
92 (let ((alist (eval alist-symbol)))
|
|
93 (cond ((null alist) nil)
|
|
94 ((anot-head-p alist key) alist)
|
|
95 (t (set alist-symbol (cdr alist))))))
|
|
96
|
|
97
|
|
98 (defun aget (alist key &optional keynil-p)
|
|
99 "Returns the value in ALIST that is associated with KEY.
|
|
100 Optional KEYNIL-P describes what to do if the value associated with
|
|
101 KEY is nil. If KEYNIL-P is not supplied or is nil, and the value is
|
|
102 nil, then KEY is returned. If KEYNIL-P is non-nil, then nil would be
|
|
103 returned.
|
|
104
|
|
105 If no key-value pair matching KEY could be found in ALIST, or ALIST is
|
|
106 nil then nil is returned. ALIST is not altered."
|
|
107 (let ((copy (copy-alist alist)))
|
|
108 (cond ((null alist) nil)
|
|
109 ((progn (asort 'copy key)
|
|
110 (anot-head-p copy key)) nil)
|
|
111 ((cdr (car copy)))
|
|
112 (keynil-p nil)
|
|
113 ((car (car copy)))
|
|
114 (t nil))))
|
|
115
|
|
116
|
|
117 (defun amake (alist-symbol keylist &optional valuelist)
|
|
118 "Make an association list.
|
|
119 The association list is attached to the alist referenced by
|
|
120 ALIST-SYMBOL. Each element in the KEYLIST becomes a key and is
|
|
121 associated with the value in VALUELIST with the same index. If
|
|
122 VALUELIST is not supplied or is nil, then each key in KEYLIST is
|
|
123 associated with nil.
|
|
124
|
|
125 KEYLIST and VALUELIST should have the same number of elements, but
|
|
126 this isn't enforced. If VALUELIST is smaller than KEYLIST, remaining
|
|
127 keys are associated with nil. If VALUELIST is larger than KEYLIST,
|
|
128 extra values are ignored. Returns the created alist."
|
|
129 (let ((keycar (car keylist))
|
|
130 (keycdr (cdr keylist))
|
|
131 (valcar (car valuelist))
|
|
132 (valcdr (cdr valuelist)))
|
|
133 (cond ((null keycdr)
|
|
134 (aput alist-symbol keycar valcar))
|
|
135 (t
|
|
136 (amake alist-symbol keycdr valcdr)
|
|
137 (aput alist-symbol keycar valcar))))
|
|
138 (eval alist-symbol))
|
|
139
|
|
140 (provide 'assoc)
|
|
141
|
|
142 ;;; assoc.el ends here
|