(define ((list-deletor! predicate) items)
(remove! predicate items))
+
+(define (any-duplicates? items #!optional = get-key)
+ (let ((= (if (default-object? =) equal? =)))
+ (if (default-object? get-key)
+ (let loop ((items items))
+ (and (pair? items)
+ (if (%member (car items) (cdr items) = 'any-duplicates?)
+ #t
+ (loop (cdr items)))))
+ (let loop ((items items))
+ (and (pair? items)
+ (or (any (let ((key (get-key (car items))))
+ (lambda (item)
+ (= key (get-key item))))
+ (cdr items))
+ (loop (cdr items))))))))
\f
;;;; Membership lists
(define (valid-field-specs? object)
(and (list? object)
(every field-spec? object)
- (not (duplicate-fields? object))))
+ (not (any-duplicates? object eq? field-spec-name))))
(register-predicate! valid-field-specs? 'valid-field-specs '<= list?)
-(define (duplicate-fields? field-specs)
- (and (pair? field-specs)
- (or (any (let ((name (field-spec-name (car field-specs))))
- (lambda (field-spec)
- (eq? name (field-spec-name field-spec))))
- (cdr field-specs))
- (duplicate-fields? (cdr field-specs)))))
-
(define (field-spec? object)
(or (symbol? object)
(and (pair? object)
alist-delete ;SRFI-1
alist-delete! ;SRFI-1
alist?
+ any-duplicates?
append
append! ;SRFI-1
append-map ;SRFI-1
(syntax-check '(_ (* identifier) * ((identifier . datum) expression)) form)
(let ((keywords (cadr form))
(clauses (cddr form)))
- (if (let loop ((keywords keywords))
- (and (pair? keywords)
- (or (memq (car keywords) (cdr keywords))
- (loop (cdr keywords)))))
+ (if (any-duplicates? keywords eq?)
(syntax-error "Keywords list contains duplicates:" keywords))
(let ((r-form (new-identifier 'form))
(r-rename (new-identifier 'rename))