;; Different algorithms can be implemented with different complexity. ;; (app list1 list2) ;; create a list with the elements of list1 ;; followed by the elements of list2 ;; AKA append ;; append is built in, this is how you might implement it ;; Runs in time O(M+N) where M is the length of list1 ;; and N is the length of list2 (define (app list1 list2) (if (null? list1) list2 (cons (car list1) (app (cdr list1) list2)))) ;; (flatten STUFF) ;; STUFF is a tree made by CONSing leaves together into ;; a nested structure ;; return a flat list that just contains the leaves of STUFF ;; ;; Naive implementation, using append, with worst-case O(N^2) time, ;; where N is the number of leaves in STUFF. (define (flatten stuff) (cond [(null? stuff) '()] [(pair? stuff) (append (flatten (car stuff)) (flatten (cdr stuff)))] [else (list stuff)])) ;; (fast-flatten STUFF) ;; like flatten, but a fancier implementation with worst case O(N) time. ;; ;; uses an auxiliary function ;; (fast-flatten-aux STUFF TAIL) ;; which returns the elements of STUFF in order ;; with TAIL appended afterwards. ;; ;; In other words, as explained in class, we have the equation ;; ;; (fast-flatten-aux STUFF TAIL) =def ;; (append (flatten STUFF) TAIL) ;; ;; to see why we write fast-flatten-aux the way we do, ;; note: ;; (fast-flatten-aux (car stuff) ;; (fast-flatten-aux (cdr stuff) tail)) ;; =def (twice) ;; (append (flatten (car stuff)) ;; (append (flatten (cdr stuff)) tail)) ;; = since append is associative ;; (append (append (flatten (car stuff)) ;; (flatten (cdr stuff))) ;; tail) ;; = by definition of flatten ;; (append (flatten stuff) tail) (define (fast-flatten-aux stuff tail) (cond [(null? stuff) tail] [(pair? stuff) (fast-flatten-aux (car stuff) (fast-flatten-aux (cdr stuff) tail))] [else (cons stuff tail)])) (define (fast-flatten stuff) (fast-flatten-aux stuff '())) ;; test data of a nested structure to play with. (define one-long-thing '(((a b c d e) (f g h i j)) ((k l) (m (n o p))) (q) r s ((t ((u v) w) x y (z)))))