56 lines
		
	
	
		
			1.5 KiB
		
	
	
	
		
			Factor
		
	
	
			
		
		
	
	
			56 lines
		
	
	
		
			1.5 KiB
		
	
	
	
		
			Factor
		
	
	
! Copyright (C) 2007, 2008 Slava Pestov, Eduardo Cavazos.
 | 
						|
! See http://factorcode.org/license.txt for BSD license.
 | 
						|
USING: accessors kernel locals.rewrite.point-free
 | 
						|
locals.rewrite.sugar locals.types macros.expander make
 | 
						|
quotations sequences sets words ;
 | 
						|
IN: locals.rewrite.closures
 | 
						|
 | 
						|
! Step 2: identify free variables and make them into explicit
 | 
						|
! parameters of lambdas which are curried on
 | 
						|
 | 
						|
GENERIC: rewrite-closures* ( obj -- )
 | 
						|
 | 
						|
: (rewrite-closures) ( form -- form' )
 | 
						|
    [ [ rewrite-closures* ] each ] [ ] make ;
 | 
						|
 | 
						|
: rewrite-closures ( form -- form' )
 | 
						|
    expand-macros (rewrite-sugar) (rewrite-closures) point-free ;
 | 
						|
 | 
						|
GENERIC: defs-vars* ( seq form -- seq' )
 | 
						|
 | 
						|
: defs-vars ( form -- vars ) { } [ defs-vars* ] reduce prune ;
 | 
						|
 | 
						|
M: def defs-vars* local>> unquote suffix ;
 | 
						|
 | 
						|
M: quotation defs-vars* [ defs-vars* ] each ;
 | 
						|
 | 
						|
M: object defs-vars* drop ;
 | 
						|
 | 
						|
GENERIC: uses-vars* ( seq form -- seq' )
 | 
						|
 | 
						|
: uses-vars ( form -- vars ) { } [ uses-vars* ] reduce prune ;
 | 
						|
 | 
						|
M: local-writer uses-vars* "local-reader" word-prop suffix ;
 | 
						|
 | 
						|
M: lexical uses-vars* suffix ;
 | 
						|
 | 
						|
M: quote uses-vars* local>> uses-vars* ;
 | 
						|
 | 
						|
M: object uses-vars* drop ;
 | 
						|
 | 
						|
M: quotation uses-vars* [ uses-vars* ] each ;
 | 
						|
 | 
						|
: free-vars ( form -- seq )
 | 
						|
    [ uses-vars ] [ defs-vars ] bi diff ;
 | 
						|
 | 
						|
M: callable rewrite-closures*
 | 
						|
    #! Turn free variables into bound variables, curry them
 | 
						|
    #! onto the body
 | 
						|
    dup free-vars [ <quote> ] map
 | 
						|
    [ % ]
 | 
						|
    [ var-defs prepend (rewrite-closures) point-free , ]
 | 
						|
    [ length \ curry <repetition> % ]
 | 
						|
    tri ;
 | 
						|
 | 
						|
M: object rewrite-closures* , ;
 |