Chapter 6
Conditional Function Definitions

from
Introduction to Programming with Mathematica,
2nd Ed.

by
Richard J. Gaylord
Samuel N. Kamin
Paul R. Wellin

Copyright 1995 TELOS/Springer-Verlag

6.1 Introduction

removeWhiteSpace[{" ", r___}] := {r}
removeWhiteSpace[{"\n", r___}] := {r}
removeWhiteSpace[L_] := L

removeWhiteSpace[{"a", "b", "c"}]

removeWhiteSpace[{" ", "a", "b", "c"}]

removeWhiteSpace[{" ", " ", "a", "b", "c"}]

removeWhiteSpace[{x_, r___} /; x == " "] := {r}
removeWhiteSpace[{x_, r___} /; x == "\n"] := {r}
removeWhiteSpace[L_] := L

removeWhiteSpace[{x_, r___} /; x == " " || x == "\n"] := {r}
removeWhiteSpace[L_] := L

removeWhiteSpace[{" " | "\n", r___}] := {r}
removeWhiteSpace[L_] := L

removeWhiteSpace[{x_, r___} /; MemberQ[{" ", "\n"}, x]] := {r}
removeWhiteSpace[L_] := L

stringMemberQ[str_, ch_] := StringPosition[str, ch] != {}
whiteSpaceQ[ch_] := stringMemberQ["\n", ch]

removeWhiteSpace[{x_?whiteSpaceQ, r___}] := {r}
removeWhiteSpace[L_] := L

removeWhiteSpace[{x_, r___} /; whiteSpaceQ[x]] := {r}
removeWhiteSpace[L_] := L

removeWhiteSpace[{x_, r___}] := {r} /; whiteSpaceQ[x]
removeWhiteSpace[L_] := L

vowelQ["a"] := True
vowelQ["e"] := True
vowelQ["i"] := True
vowelQ["o"] := True
vowelQ["u"] := True
vowelQ[c_] := False

6.2 Conditional Functions

removeTwoSpaces[lis_] := 
   If[whiteSpaceQ[First[lis]],
      If[whiteSpaceQ[First[Rest[lis]]],
         Rest[Rest[lis]],
	 Rest[lis]],
      lis]

applyChar[lis_] :=
Module[{op = First[lis], nums = Rest[lis]},   
  If[op == "+", Apply[Plus, nums],   
    If[op == "-", Apply[Subtract, nums],
      If[op == "*", Apply[Times, nums],   
        If[op == "/", Apply[Divide, nums],   
          Print["Bad argument to applyChar"]]]]]]

applyChar[{"+", 1, 2, 3, 4}]

applyChar[lis_] :=
Module[{op = First[lis], nums = Rest[lis]},
      Which[op == "+", Apply[Plus, nums],
            op == "-", Apply[Subtract, nums],
	    op == "*", Apply[Times, nums],
	    op == "/", Apply[Divide, nums],
	    True, Print["Bad argument to applyChar"]]]

applyChar[lis_] :=
Module[{op = First[lis], nums = Rest[lis]},
      Switch[op, "+", Apply[Plus, nums],
                 "-", Apply[Subtract, nums],
                 "*", Apply[Times, nums],
                 "/", Apply[Divide, nums],
                 _,   Print["Bad argument to ApplyChar"]]]

incrementNumbers[L_] := Map[If[NumberQ[#], #+1, #]&, L]

divide100By[L_] := Map[If[#==0, #, 100/#]&, L]

removeRepetitions[L_] :=
   Fold[If[#2==Last[#1], #1, Append[#1, #2]]&, 
       {First[L]}, Rest[L]]

6.3 Example---Classifying Points

Code  from book

pointLoc[{x_, y_}] :=
   Which[
        x == 0 && y == 0, 0,
	y == 0, -1,
	x == 0, -2,
	x > 0 && y > 0, 1,
	x < 0 && y > 0, 2,
	x < 0 && y < 0, 3,
        True (* x > 0 && y < 0 *) , 4]

pointLoc[{x_, y_}] :=
Which[
     x == 0, If[y == 0, 0, -2],
     x > 0, Which[y > 0, 1,
                  y < 0, 4,
		  True (* y == 0 *), -1],
     True (* x<0 *),
     Which[y < 0, 3,
           y > 0, 2,
           True (* y == 0 *), -1]
     ]

pointLoc[{0, 0}] := 0
pointLoc[{x_, 0}] := -1
pointLoc[{0, y_}] := -2
pointLoc[{x_, y_}] := If[x < 0, 2, 1] /; y > 0
pointLoc[{x_, y_}] := If[x < 0, 3, 4] (* /; y < 0 *)

pointLoc[{0 | 0.0, 0 | 0.0}] := 0
pointLoc[{x_, 0 | 0.0}] := -1
pointLoc[{0 | 0.0, y_}] := -2

Exercises

Ex.1

signum1[x_ /; x<0] := -1
signum1[x_ /; x>0] := 1
signum1[0]         := 0

Map[signum1, {-2, 0, 1}]

signum2[x_] :=
   If[x<0, -1,
     If[x==0, 0, 1]]

Map[signum2, {-2, 0, 1}]

signum3[x_] :=
   Which[x<0, -1,
         x==0, 0,
         True, 1]

Map[signum3, {-2, 0, 1}]

Ex.2

signum1[x_ /; x<0] := -1
signum1[x_ /; x>0] := 1
signum1[0]         := 0
signum1[0.0]       := 0

Map[signum1, {-2, 0, 2}]

signum2[x_] :=
   If[x<0, -1,
     If[x>0, 1, 0]]

Map[signum2, {-2, 0, 2}]

signum3[x_] :=
   Which[x<0, -1,
         x>0, 1,
         True, 0]

Map[signum3, {-2, 0, 2}]

Ex.3

SwapTwo1[{}] := {}
SwapTwo1[{x_}] := {x}
SwapTwo1[{x_, y_, r___}] := {y, x, r}

SwapTwo2[{x_, y_, r___}] := {y, x, r}
SwapTwo2[x_] := x

Map[SwapTwo1, {{}, {a}, {a,b,c,d}}]

Ex.4

vowelQ[c_] :=
  Switch[c, "a", True,
            "e", True,
            "i", True,
            "o", True,
            "u", True,
             _,  False]

canFollow[ch1_, ch_] :=
  Switch[ch1, "a", True,
              "b", StringMemberQ["aeiloruy", ch],
              "c", StringMemberQ["aehiloruy", ch],
              "d", StringMemberQ["aeioruy", ch],
              "z", StringMemberQ["aeiouy", ch],
               _,  False]

Ex.5

removeTwoSpaces[lis_] :=
                        If[lis == {}, {},
                          If[whiteSpaceQ[First[lis]],
                            If[Length[lis]==1, {},
                              If[whiteSpaceQ[First[Rest[lis]]],
                                 Rest[Rest[lis]],
                                 Rest[lis]]],
                            lis]]

Ex.6

f[{x1_Integer, ___}, 1] := x1+1
f[x_Integer, y_/;(y!=1)] := x-y

Ex.7

applyChar[{"+", nums__}] := Apply[Plus, {nums}]
applyChar[{"-", nums__}] := Apply[Minus, {nums}]
applyChar[{"*", nums__}] := Apply[Times, {nums}]
applyChar[{"/", nums__}] := Apply[Divide, {nums}]
applyChar[_] := Print["Bad argument to applyChar"];

Ex.8

pointLoc[{0, 0}] := 0
pointLoc[{x_, 0}] := -1
pointLoc[{0, y_}] := -2
pointLoc[{x_, y_}] := If[x<0, 2, 1] /; y>0
pointLoc[{x_, y_}] := If[x<0, 3, 4] (* /; y<0 *)
pointLoc[{x_, y_, z_}] := If[x<0, 2, 1] /; y>=0 && z>=0
pointLoc[{x_, y_, z_}] := If[x<0, 3, 4] /; y<0 && z>=0
pointLoc[{x_, y_, z_}] := If[x<0, 6, 5] /; y>=0 && z<0
pointLoc[{x_, y_, z_}] := If[x<0, 7, 8] /; y<0 && z<0

Ex.9a

doublePos[lis_] := Map[If[#>0, 2 * #, #]&, lis]

Ex.9b

remove3Repetitions[lis_] :=
          Fold[If[Length[#1]>2 && #2 == #1[[-1]] == #1[[-2]],
                  #1, Join[#1, {#2}]]&,
               {},
               lis]

Ex.9c

positiveSum[L_] := Fold[If[#1+#2 < 0, 0, #1+#2]&, 0, L]