@comment(Hey, EMACS, this is -*- SCRIBE -*- input)
@device(dover)
@make(6001)

@modify(excounter, numbered [Exercise @1], referenced [@1])

@PageHeading(left "6.001 -- Spring Semester 1987",
             center "@Value(Page)",
             right "Problem set 5")

@begin(center)
MASSACHUSETTS INSTITUTE OF TECHNOLOGY
Department of Electrical Engineering and Computer Science
6.001 Structure and Interpretation of Computer Programs
Spring Semester, 1987

Problem Set 5
@end(center)
@blankspace(0.25 in)

@begin(flushleft)
Issued: Tuesday, 3 March 1987

@begin(itemize)
on Wednesday, 11 March 1987
for recitations meeting at 9:00, 10:00, and 11:00

on Friday, 13 March 1987
for recitations meeting at 12:00, 1:00, and 2:00
@end(itemize)

Reading assignment:
@begin(itemize)
Chapter 2 through section 2.4.1

programs (attached): @a[ps5-res.scm]
@end(itemize)
@end(flushleft)

@b[Quiz announcement:] Quiz 1 is on Wednesday, 18 March 1987.  The
quiz will be held in Walker Memorial Gymnasium (50-340) from 5-7PM xor
7-9PM.  You may take the quiz during either one of these two periods,
but students taking the quiz during the first period will not be
allowed to leave the room until the end of the period.  The quiz will
cover material from the beginning of the semester through this problem
set and through section 2.4.1 of the textbook.


@section(Series-Parallel Resistive Networks)

Louis Reasoner and  Lem E. Tweakit are trying to implement an electrical
circuit analyzer. Lem suggests that they begin with a
program that computes resistances of simple ``linear resistive
networks.''@foot{In this problem set, we use the words ``network'' and
``circuit'' interchangeably.  In the context of Louis's program, there
is no distinction.} These are constructed from primitive elements
called @a[resistors].  A resistor is characterized by a number @a[R]
called the @a[resistance] of the resistor.  It can be depicted as
follows:
@begin(smallfigurebody)

                          o---/\/\/\/\----o
                                  R
@end(smallfigurebody)
For computational purposes, it is also convenient to consider the
@a[conductance] of a resistor, which is defined to be the reciprocal of
the resistance. (Conductance is traditionally denoted by the letter
@a[G].)
@begin(smallfigurebody)

                          o---/\/\/\/\----o
                                G = 1/R
@end(smallfigurebody)

A resistor is the simplest example of a kind of element called a
@i[two-terminal network], i.e., a network that has exactly two terminals to
which other objects can be connected:
@begin(smallfigurebody)
                               --------
                               |      |
                          o----|  N   |----o
                               |      |
                               --------

@end(smallfigurebody)

Networks can be combined by attaching their terminals together.  A
network has a resistance (and conductance) that is determined by the
resistances of its parts and the ways in which they are
interconnected.  Louis's and Lem's initial system will provide two
basic methods of combination for constructing two-terminal networks
from simpler two-terminal networks.  The first method is called @a[series]
combination:
@begin(smallfigurebody)
                       --------       --------
                       |      |       |      |
               o-------|  A   |-------|  B   |--------o
                       |      |       |      |
                       --------       --------

                             R = R  +  R
                                  A     B
@end(smallfigurebody)
The combined resistance of two networks connected in series is the sum
of the resistances.

The second method is @a[parallel] combination: 
@begin(smallfigurebody)
                    --------
                    |      |
               -----|  A   |-----                   
               |    |      |    |                   
               |    --------    | 
        o------|                |-----o         G = G  +  G
               |                |                    A     B
               |    --------    |                    
               |    |      |    |                     
               -----|  B   |-----     
                    |      |         
                    --------              
@end(smallfigurebody)                                            
The combined conductance of two networks joined in parallel is the sum
of the conductances of the pieces.

After a few hours of work, Louis and Lem have quite an
elegant program that handles such series and parallel
combinations.@foot{Networks that can be constructed as series and
parallel combinations of primitive two-terminal elements are called
@i[series-parallel networks].} The program is provided in the first
appendix to this handout, labeled @a[ps5-res.scm].

You should read through this code now to get some idea of how it
works.  There are constructors @a[make-resistor], @a[make-series], and
@a[make-parallel], and an operation called @a[resistance] that
computes the resistance of a network by finding the resistances of the
parts of a network and combining them appropriately.

Louis and Lem test their program by computing the resistance of the
following network:
@begin(smallfigurebody)

             R=40                R=30
    o-------\/\/\/--------------\/\/\/---------------------o
                       |                         |
                       |                         |
                       |----\/\/\/---\/\/\/------|
                             R=10     R=20
@end(smallfigurebody)
They type:
@begin(programexample)

(define r1 (make-resistor 10))
(define r2 (make-resistor 20))
(define r3 (make-resistor 30))
(define r4 (make-resistor 40))

(define N
  (make-series r4
               (make-parallel r3
                              (make-series r1 r2))))

-->(resistance N)
55.000
@end(programexample)
Indeed, the answer is correct (as Lem verifies).

@begin(exercise)
Consider the data structure representing the network @a[N].
@begin(alphaenumerate)
Draw the box-and-pointer structure that represents the object @a[N].

How many times was @a[resistance] called in computing the resistance of
@a[N]?  What were the arguments to @a[resistance] for each call?  (To
specify the arguments, you can sketch the part of the network that
each argument represents, or you can give a description in English,
e.g., ``@a[R3] in parallel with @a[R4]''.)

@end(alphaenumerate)
@end(exercise)

@paragraph(P-extensions)

Given a 2-terminal network @a[B], we can form a new two-terminal
network by attaching an ``P-section,'' which is itself constructed
from two two-terminal networks @a[S] and @a[P] as follows:
@begin(smallfigurebody)
                     ------
                     |    |
    o----------------| S  |-------
              |      |    |      | 
              |      ------      |
            ------             ------
            |    |             |    |
            | P  |             | B  |
            |    |             |    |
            ------             ------
               |                  |
    o------------------------------
@end(smallfigurebody)
This operation is called ``P-extension'' of a ``base'' @a[B] by a ``series
part'' @a[S] and a ``parallel part'' @a[P].

@begin(exercise)
Write a procedure @a[P-extend] that takes three two-terminal networks --
@a[base], @a[series-part], and @a[parallel-part] -- and combines them
using @a[make-series] and @a[make-parallel] to produce the extended
network as shown above.
@end(exercise)

@begin(exercise)
Use your @a[P-extend] procedure to make a new network that extends the
network @a[N] from Exercise 1 (as the base) by a 10-ohm resistor (the
series part) and another 10-ohm resistor (the parallel part).

Verify that the resulting network has a resistance of 8.66... ohms.  Show
the expressions that you typed in order to generate the network and to
check its resistance.
@end(exercise)


By repeatedly P-extending a base by a given series and parallel
part, we obtain a circuit called a ``ladder.''  The following diagram
shows a 3-stage ladder.
@begin(smallfigurebody)

   o-----------S-------S-------S-----
          |        |       |        |
          P        P       P        B
          |        |       |        |
   o--------------------------------- 

@end(smallfigurebody)

Louis decides that he can easily implement a ladder by making use of
his @a[P-extend] procedure, together with the @a[repeated] procedure
below:

@begin(programexample)
(define (repeated f n)
  (lambda (x)
    (if (= n 0)
        x
        ((repeated f (-1+ n)) (f x)))))
@end(programexample)

He defines the following procedure to construct a ladder with a
given number of stages:

@begin(programexample)
(define (ladder-extension stages base series-part parallel-part)
  ((repeated @i[<EXP-1>] stages) @i[<EXP-2>]))
@end(programexample)

@begin(exercise)
Complete the @a[ladder-extension] procedure.  What are the missing
expressions
@i[<EXP-1>] and @i[<EXP-2>]?
@end(exercise)

@begin(exercise)
Louis and Lem demonstrate their system to Ben Bitdiddle.  As an
example, they try to compute the resistance of a long ladder.  To
their surprise, they find that although the program gets correct
answers, it seems to run more slowly than before.

Taking a careful look at the code, they find that Louis has changed
the definition of @a[resistance-parallel] so that it now reads:
@begin(programexample)
(define (resistance-parallel ckt)
  (/ (* (resistance (left-branch ckt))
        (resistance (right-branch ckt)))
     (+ (resistance (left-branch ckt))
        (resistance (right-branch ckt)))))
@end(programexample)
Explain why this change makes the program run so slowly.  As an
example, consider a ladder in which each of the series, parallel, and
base pieces is a simple resistor.  If the ladder has @a[N] stages:
@begin(alphaenumerate)
How many resistors are contained in the ladder?

In computing the resistance of the ladder, how many times will the
procedure @a[resistance-resistor] be run if the system uses the
original version of the @a[resistance-parallel] procedure?

After Louis installs the new version of @a[resistance-parallel], how
many times will @a[resistance-resistor] be run in computing the resistance
of the @a[N]-stage ladder?  (You should be able to obtain an exact answer
in terms of @a[N].  However, partial credit will be given for good partial
answers.  Show your work.)

How has Louis's change affected the running time of the system?
(E.g., slowed it down by a constant factor?  slowed it down
quadratically? slowed it down exponentially?)
@end(alphaenumerate)
@end(exercise)

@section(Data Directed - Message Passing Implementation)

The network analysis package that Messrs. Reasoner and Tweakit have 
developed uses manifest types and generic operators. An alternate 
package can be developed using message passing as described in
pp. 140-142 of the text.  This should facilitate a dual representation
for resistors: in terms of their @a[resistance] and in terms of 
their @a[conductance] (numerically the reciprocal of resistance).
If such a dual representation were available, the example network
above might be described as follows:

@begin(programexample)

(define r1 (make-resistance 10))
(define r2 (make-resistance 20))
(define g3 (make-conductance (/ 1 30)))
(define r4 (make-resistance 40))

(define N
  (make-series r4
               (make-parallel g3
                              (make-series r1 r2))))

-->(resistance N)
55.000
@end(programexample)

@begin(exercise)

Implement a series-parallel package using a message-passing style
with a dual representation of resistors. Show that your procedures
evaluate the resistance of network @a[N] correctly. Plan your 
design carefully @b[before coming to lab].  

@end (exercise)

@newpage()
@begin(programexample)
@include(ps5-res.SCM)
@end(programexample)
@newpage()
