En Algo & de Datos II, utiliza estos todos los tiempos de la "salida" o "retorno" de una función (largo)
por ejemplo, el algorthm BFS para atravesar árboles con se implementó como esto:
(define (BFS graph root-discovered node-discovered edge-discovered edge-bumped . nodes)
(define visited (make-vector (graph.order graph) #f))
(define q (queue.new))
(define exit())
(define (BFS-tree node)
(if (node-discovered node)
(exit node))
(graph.map-edges
graph
node
(lambda (node2)
(cond ((not (vector-ref visited node2))
(when (edge-discovered node node2)
(vector-set! visited node2 #t)
(queue.enqueue! q node2)))
(else
(edge-bumped node node2)))))
(if (not (queue.empty? q))
(BFS-tree (queue.serve! q))))
(call-with-current-continuation
(lambda (my-future)
(set! exit my-future)
(cond ((null? nodes)
(graph.map-nodes
graph
(lambda (node)
(when (not (vector-ref visited node))
(vector-set! visited node #t)
(root-discovered node)
(BFS-tree node)))))
(else
(let loop-nodes
((node-list (car nodes)))
(vector-set! visited (car node-list) #t)
(root-discovered (car node-list))
(BFS-tree (car node-list))
(if (not (null? (cdr node-list)))
(loop-nodes (cdr node-list)))))))))
Como se puede ver el algoritmo va a salir cuando la función del nodo-descubierto devuelve verdadero:
(if (node-discovered node)
(exit node))
la función también se dará un "retorno valor ": 'nodo'
por qué se cierra la función, se debe a que de esta declaración:
(call-with-current-continuation
(lambda (my-future)
(set! exit my-future)
cuando usamos la salida, pasará de nuevo al estado antes de la ejecución, el vaciado de la pila de llamadas y devuelve el valor que le diste.
Así que, básicamente, call-cc se utiliza (en este caso) para saltar de una función recursiva, en lugar de esperar a que toda la recursividad para poner fin por sí mismo (que puede ser bastante caro cuando se hace un montón de trabajo computacional)
hacer lo mismo con la llamada cc otro ejemplo más pequeña:
(define (connected? g node1 node2)
(define visited (make-vector (graph.order g) #f))
(define return())
(define (connected-rec x y)
(if (eq? x y)
(return #t))
(vector-set! visited x #t)
(graph.map-edges g
x
(lambda (t)
(if (not (vector-ref visited t))
(connected-rec t y)))))
(call-with-current-continuation
(lambda (future)
(set! return future)
(connected-rec node1 node2)
(return #f))))
¡Sí! Estoy buscando ejemplos de código sin embargo. –