Domanda

Sto usando R5RS Scheme e voglio solo per implementare una funzione che restituisce l'intersezione di due date liste, ma non posso farlo perché non posso aggiungere un elemento a un elenco. Ecco il mio codice. Come posso risolvere il problema? Sono davvero un principiante in Scheme -. Questo è il mio primo lavoro utilizzando Scheme

thx in anticipo ..

(define list3 '())
(define (E7 list1 list2)

        (cond
          ((null? list1)
          list3)
          ((member (car list1) list2) (append list3 (list (car list1))))

        )
  (cond
          ((null? list1)
          list3)
          ((not(null? list1)) (E7 (cdr list1) list2)

        )

     )


)
(E7 '(4 5) '(3 4))
È stato utile?

Soluzione

Ecco una versione ricorsiva che fa l'intersezione invece dell'unione.

(define (intersect list1 list2)
  (cond ((null? list1)   list1)
        ((member (car list1) list2)   (cons (car list1) (intersect (cdr list1) list2)))
        (t   (intersect (cdr list1) list2))))

Altri suggerimenti

Mi sembra di vedere il vostro problema. Ci sono due modi per aggiungere un elemento a un elenco.

Il primo modo sarebbe in realtà aggiungendo che:

(define (intersect list1 list2)
  (define newlist list2)
  (do ((iter1 list1 (cdr iter1)))
    (not (null? iter1))
    (if (not (member (car iter1) newlist))
        (set! newlist (cons (car iter1) newlist)))))

(Probabilmente dovrete per cercare la definizione di do se si vuole veramente utilizzare questo.)

Si può notare che questo è abbastanza brutto. Questo perché nessuno in realtà lo fa in questo modo. Al contrario, è necessario rendersi conto che chiamare una funzione crea una nuova variabile pure. Prova questo:

(define (intersect list1 list2)
  (cond ((null? list1) list2)
        ((member (car list1) list2) (intersect (cdr list1) list2))
        (else (intersect (cdr list1) (cons (car list1) list2)))))

Se si ha familiarità con gli algoritmi, si noterà che il codice che ho appena scritto è abbastanza lento, ma illustra il punto: in ogni caso, si fa un po 'di lavoro e poi chiama di nuovo la funzione. Se hai difficoltà a vedere il motivo per cui questo funziona, eseguire questa funzione invece sul tuo esempio:

(define (intersect list1 list2)
  (display list1) (display " ") (display list2) (newline)
  (cond ((null? list1) list2)
        ((member (car list1) list2) (intersect (cdr list1) list2))
        (else (intersect (cdr list1) (cons (car list1) list2)))))

Ecco elisp semplicistico:

(defun is (l1 l2)
  (let ((rtn))
    (mapc
      (lambda (e) 
        (if (member e l1)
          (push e rtn)))
      l2)
    rtn))

Questo comporta come l'intersezione incorporato per questi semplici test:

(is '(1 2 5) '(1 4 10 5))  => (5 1)
(intersection '(1 2 5) '(1 4 10 5)) => (5 1)

(is '(1 4 10 5) '(1 2 5)) => (5 1)
(intersection '(1 4 10 5) '(1 2 5)) => (5 1)

È meglio utilizzare impostare operazioni da SRFI-1.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top