# Summation Function with Functional Parameters # Functional Programming Example - Higher Order # H. Conrad Cunningham, Professor # Computer and Information Science # University of Mississippi # Developed for CSci 556, Multiparadigm Programming, Spring 2015 # 34567890123456789012345678901234567890123456789012345678901234567890 # 2015-02-08: Developed from 2013 Lua version defmodule Summation do @moduledoc """ This higher-order summation function is adapted from a Lua version, which itself is adapted from the Scheme code from section 1.3.1 of Abelson and Sussman's Structure and Interpretation of Computer Programs (SICP) textbook. """ @doc """ Function "sum_integers" computes the sum of the integers in the range from "a" through "b". """ def sum_integers(a,b) when is_number(a) and is_number(b) do if a > b do 0 else a + sum_integers(a+1,b) end end @doc """ Function "sum_cubes" computes the sum of the cubes of the integers in the range from "a" through "b". """ def sum_cubes(a,b) when is_number(a) and is_number(b) do if a > b do 0 else cube(a) + sum_cubes(a+1,b) end end defp cube(x) do x * x * x end @doc """ Function "pi_sum" computes the sum of the series of terms 1/(i*(i+2)) from i = "a" until i > "b". For a = 1 and b = 10 this would be 1/1*3 + 1/5*7 + 1/9*11. For initial a = 1, this converges slowly on PI/8. """ def pi_sum(a,b) when is_number(a) and is_number(b) do if a > b do 0 else 1 / (a * (a+2)) + pi_sum(a+4,b) end end # The above all satisfy template of the following form for some # NAME,TERM, and NEXT. # # def NAME(a,b) when is_integer(a) and is_integer(b) do # if a < b do 0 else TERM(a) + NAME(NEXT(a),b) end # end # # We can express this function as a higher-order function (for NAME) # with functional arguments for the operations TERM and NEXT. @doc """ Function "sum" adds the values of the application of function "term" to integer i for all integers i in the range [1,b], where the difference from i to its successor j is next(i). """ def sum(term,a,next,b) when is_number(a) and is_number(b) and is_function(term) and is_function(next) do if a > b do 0 else term.(a) + sum(term,next.(a),next,b) end end @doc " sum_integers in terms of sum " def sum_integers2(a,b) when is_number(a) and is_number(b) do sum(&id/1,a,&incr/1,b) end defp id(x) do x end defp incr(x) do x + 1 end @doc "sum_cubes in terms of sum" def sum_cubes2(a,b) when is_number(a) and is_number(b) do sum(&cube/1,a,&incr/1,b) end @doc "pi_sum in terms of sum" def pi_sum2(a,b) when is_number(a) and is_number(b) do sum(&pi_term/1,a,&pi_next/1,b) end defp pi_term(x) do 1 / (x * (x+2)) end defp pi_next(x) do x + 4 end # Function "sum" can be further generalized in various ways. # Question: How would we need to modify "sum" so that the resulting # higher-order function is capable of either summing or multiplying # the integers over a range? end