]> git.rkrishnan.org Git - sicp.git/blob - src/sicp/ex2_77.rkt
Lazy version of evaluator and tests.
[sicp.git] / src / sicp / ex2_77.rkt
1 #lang racket
2 #|
3 magnitude is defined in section 2.4.3 as:
4
5 (define (magnitude z) (apply-generic 'magnitude z))
6
7 In this example z looks as '(complex rectangular 3 . 4))
8
9 The apply-generic procedure is defined as follows:
10
11 (define (apply-generic op . args)
12   (let ((type-tags (map type-tag args)))
13     (let ((proc (get op type-tags)))
14       (if proc
15           (apply proc (map contents args))
16           (error
17             "No method for these types -- APPLY-GENERIC"
18             (list op type-tags))))))
19
20 Here, we find the type-tag of z, in this case, it will be 'complex.
21 The table constructed with the generic prodecure "magnitude" was using
22 the type of z, namely 'rectangular. 
23
24 The remedy as suggested by Alyssa is as follows:
25
26 (put 'real-part '(complex) real-part)
27 (put 'imag-part '(complex) imag-part)
28 (put 'magnitude '(complex) magnitude)
29 (put 'angle '(complex) angle)
30
31 Now, this will add a new column for each of the operations (real-part, imag-part,
32 magnitude and angle) for the type '(complex) and install the corresponding function.
33
34 Now, when we do (type-tag z), we get 'complex and then we look for the type-specific
35 procedure using (get op type-tag) which will give the right procedure.
36
37 (apply-generic 'magnitude z)
38
39 => (apply-generic 'magnitude '(complex rectangular x . y)
40
41 => ((get 'magnitude 'complex) '(rectangular x . y) 
42
43 => (magnitude '(rectangular x . y))
44
45 => (apply-generic 'magnitude '(rectangular x . y))
46
47 => ((get 'magnitude 'rectangular) '(x . y))
48
49 So, apply-generic gets invoked twice.
50
51
52 (
53
54 |#