functionschemesicp# Are Scheme functions one liners?

I am following *Structure and Interpretation of Computer Programs* and while attempting to solve Ex 1.3 I arrived at the following code as my first attempt:

```
(define (sumsq a b c)(
(define highest (if (> (if (> a b) a b) (if (> a c) a c)) (if (> a b) a b) (if (> a c) a c)))
(define second_h (if (> (if (> a b) b a) (if (> a c) c a)) (if (> a b) b a) (if (> a c) c a)))
(+ (* highest highest) (* second_h second_h)))
```

It was not working and I looked up the solution and found them at SICP Wiki

```
;; ex 1.3
;; implemented using only techniques covered to this point
(define (square x) (* x x))
(define (sum-of-squares x y)
(+ (square x) (square y)))
(define (largest-two-of-three x y z)
(if (>= x y)
(sum-of-squares x (if (>= y z) y z))
(sum-of-squares y (if (>= x z) x z))))
```

The difference was that I was using multiple statements to define variables and then sum the squares, while the correct way is to define each of my lines as functions.

Are functions in Scheme one liners? Or did I miss the whole thing?

Solution

What you wrote (minus one extra paren) is:

```
(define (sumsq a b c)
(define highest
(if (> (if (> a b) a b)
(if (> a c) a c))
(if (> a b) a b)
(if (> a c) a c)))
(define second_h
(if (> (if (> a b) b a)
(if (> a c) c a))
(if (> a b) b a)
(if (> a c) c a)))
(+ (* highest highest) (* second_h second_h)))
```

Their solution does separate squares and sum-of-squares into separate functions, but I don't think that that's what's important. Not writing `(+ (* a a) (* b b))`

**will** stop you from having to name the two values you're calculating, which will let you write the function as one big expression at the end, but there are bigger things to worry about now.

I think the problem you're having is that your (if...) expressions are too big to easily understand. Notice that there are two patterns which show up many times: `(if (> a b) a b)`

and `(if (> a b) b a)`

. These are the max and min functions, so it's useful to define them as such:

```
(define (min a b) (if (< a b) a b))
(define (max a b) (if (< a b) b a))
```

This way, you can rewrite your solution as:

```
(define (sumsq a b c)
(define highest
(if (> (max a b) (max a c))
(max a b)
(max a c)))
(define second_h
(if (> (min a b) (min a c))
(min a b)
(min a c)))
(+ (* highest highest) (* second_h second_h)))
```

Simplifying it again gives:

```
(define (sumsq a b c)
(define highest
(max (max a b) (max a c)))
(define second_h
(max (min a b) (min a c)))
(+ (* highest highest) (* second_h second_h)))
```

Notice how this writing is much more easy to reason with, `(max (max a b) (max a c))`

is obviously the maximum of `a`

`b`

and `c`

, and can actually be rewritten as `(max (max a b) c)`

. Looking at `second_h`

, though, it's not obvious that it's correct. What will happen when `a`

is the smallest of the three values?

The trick they use in their solution is to first compare `x`

and `y`

. if `x < y`

, then you know that `y`

is not the smallest of the three, so it is either highest or second highest. The other number you will want to use is the higher of `x`

and `z`

, since the lower of those two will be the smallest of the three, which you want to ignore. Similar logic applies when `y < x`

.

- Why constant declaration in function declaration doesn't throw an error?
- Remove elements of a named list based on the naming match in R
- How to use `scipy.integrate.quad` to compute integral of a function which depends on the integral of another function
- Php using array_map with a predefined variable variable does not work
- Modify the names of a named list in R based on a logic
- Apply function to each cell in DataFrame
- How to stop Click Event when selecting the text?
- Random value in array when defining from function (Arduino)
- strdup() - what does it do in C?
- Determine function name from within that function
- Why is function within main function in python always returning "none" when it should return a float?
- Is there a function to copy an array in C/C++?
- how to make fputs function prompt wrong input and ask user to input again...program stopping instead of request for new input
- subtract all unique pairs of elements of a list in R
- Void pointer values inexplicably changing between function calls
- Function for lookup with multiple conditions in excel
- Analysing an array of objects data using my function and Math.max
- Python dynamic argument processing inside fucntion
- Create a named list of numerics from a data.frame in R
- Default optional parameter in Swift function
- Capitalise every word in String with extension function
- Python sorted function key
- How to count characters in a C_String in C++?
- Create a function in PostgreSQL
- PostgreSQL syntax error when using EXECUTE in Function
- I refactored working code into a function - now I can't figure out how to pass the "x" axis column argument
- Using `RETURN NEXT` and `RETURN QUERY` in the same Postgres function
- Store query result in a variable using in PL/pgSQL
- Function to accept a set of types
- Python chain several functions into one