C++ code fixes

This commit is contained in:
Igal Tabachnik 2017-09-30 14:41:50 +03:00
parent 6e27058441
commit d5666cd5e4
12 changed files with 102 additions and 102 deletions

Binary file not shown.

View File

@ -50,7 +50,7 @@ C g(B b);
\end{Verbatim} \end{Verbatim}
Their composition is: Their composition is:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
C g_after_f(A a) C g_after_f(A a)
{ {
return g(f(a)); return g(f(a));
@ -87,9 +87,9 @@ g ◦ f
\end{Verbatim} \end{Verbatim}
You can even use Unicode double colons and arrows: You can even use Unicode double colons and arrows:
\begin{minted}[escapeinside=||,mathescape=true]{text} \begin{Verbatim}[commandchars=\\\{\}]
f |\ensuremath{\Colon}| A → B f \ensuremath{\Colon} A → B
\end{minted} \end{Verbatim}
So here's the first Haskell lesson: Double colon means ``has the type So here's the first Haskell lesson: Double colon means ``has the type
of\ldots{}'' A function type is created by inserting an arrow between of\ldots{}'' A function type is created by inserting an arrow between
two types. You compose two functions by inserting a period between them two types. You compose two functions by inserting a period between them
@ -142,7 +142,7 @@ identity function that just returns back its argument. The
implementation is the same for every type, which means this function is implementation is the same for every type, which means this function is
universally polymorphic. In C++ we could define it as a template: universally polymorphic. In C++ we could define it as a template:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class T> T id(T x) { return x; } template<class T> T id(T x) { return x; }
\end{Verbatim} \end{Verbatim}
Of course, in C++ nothing is that simple, because you have to take into Of course, in C++ nothing is that simple, because you have to take into

View File

@ -169,7 +169,7 @@ Keep in mind that it's really a family of functions parameterized by
\code{a}. This is another example of the terseness of the Haskell \code{a}. This is another example of the terseness of the Haskell
syntax. A similar construct in C++ would be slightly more verbose: syntax. A similar construct in C++ would be slightly more verbose:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class A> G<A> alpha(F<A>); template<class A> G<A> alpha(F<A>);
\end{Verbatim} \end{Verbatim}
There is a more profound difference between Haskell's polymorphic There is a more profound difference between Haskell's polymorphic
@ -746,7 +746,7 @@ for vertical composition, but not vice versa.
Finally, the two compositions satisfy the interchange law: Finally, the two compositions satisfy the interchange law:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}[commandchars=\\\{\}]
(β' α') ◦ (β ⋅ α) = (β' ◦ β) ⋅ (α' ◦ α) (β' \ensuremath{\cdot} α') ◦ (β \ensuremath{\cdot} α) = (β' ◦ β) \ensuremath{\cdot} (α' ◦ α)
\end{Verbatim} \end{Verbatim}
I will quote Saunders Mac Lane here: The reader may enjoy writing down I will quote Saunders Mac Lane here: The reader may enjoy writing down

View File

@ -247,7 +247,7 @@ The function \code{product} multiplies all elements of a list. That's
just like a definition of factorial taken from a math text. Compare this just like a definition of factorial taken from a math text. Compare this
with C: with C:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
int fact(int n) { int fact(int n) {
int i; int i;
int result = 1; int result = 1;
@ -342,7 +342,7 @@ Think of functions from and to this type. A function from \code{void}
can always be called. If it's a pure function, it will always return the can always be called. If it's a pure function, it will always return the
same result. Here's an example of such a function: same result. Here's an example of such a function:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
int f44() { return 44; } int f44() { return 44; }
\end{Verbatim} \end{Verbatim}
You might think of this function as taking ``nothing'', but as we've You might think of this function as taking ``nothing'', but as we've
@ -418,7 +418,7 @@ unit _ = ()
\end{Verbatim} \end{Verbatim}
In C++ you would write this function as: In C++ you would write this function as:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class T> template<class T>
void unit(T) {} void unit(T) {}
\end{Verbatim} \end{Verbatim}
@ -434,7 +434,7 @@ data Bool = True | False
\code{True} or \code{False}.) In principle, one should also be able \code{True} or \code{False}.) In principle, one should also be able
to define a Boolean type in C++ as an enumeration: to define a Boolean type in C++ as an enumeration:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
enum bool { enum bool {
true, true,
false false
@ -455,8 +455,8 @@ the Haskell library \code{Data.Char} is full of predicates like
\code{} that defines, among others, \code{isalpha} and \code{} that defines, among others, \code{isalpha} and
\code{isdigit}, but these return an \code{int} rather than a \code{isdigit}, but these return an \code{int} rather than a
Boolean. The actual predicates are defined in \code{std::ctype} and Boolean. The actual predicates are defined in \code{std::ctype} and
have the form \code{ctype::is(alpha,\ c)}, have the form \code{ctype::is(alpha, c)},
\code{ctype::is(digit,\ c)}, etc. \code{ctype::is(digit, c)}, etc.
\section{Challenges}\label{challenges} \section{Challenges}\label{challenges}
@ -491,18 +491,18 @@ have the form \code{ctype::is(alpha,\ c)},
\item \item
The factorial function from the example in the text. The factorial function from the example in the text.
\item \item
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
std::getchar() std::getchar()
\end{Verbatim} \end{Verbatim}
\item \item
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
bool f() { bool f() {
std::cout << "Hello!" << std::endl; std::cout << "Hello!" << std::endl;
return true; return true;
} }
\end{Verbatim} \end{Verbatim}
\item \item
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
int f(int x) int f(int x)
{ {
static int y = 0; static int y = 0;

View File

@ -1,4 +1,4 @@
\lettrine[lhang=0.17]{Y}{ou can get real appreciation} for categories by studying a variety of \lettrine[lhang=0.17]{Y}{ou can get} real appreciation for categories by studying a variety of
examples. Categories come in all shapes and sizes and often pop up in examples. Categories come in all shapes and sizes and often pop up in
unexpected places. We'll start with something really simple. unexpected places. We'll start with something really simple.
@ -195,7 +195,7 @@ so this might be a little confusing to the beginner.)
The closest one can get to declaring a monoid in C++ would be to use the The closest one can get to declaring a monoid in C++ would be to use the
(proposed) syntax for concepts. (proposed) syntax for concepts.
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class T> template<class T>
T mempty = delete; T mempty = delete;
@ -223,7 +223,7 @@ type) that tests whether there exist appropriate definitions of
An instantiation of the Monoid concept can be accomplished by providing An instantiation of the Monoid concept can be accomplished by providing
appropriate specializations and overloads: appropriate specializations and overloads:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<> template<>
std::string mempty<std::string> = {""}; std::string mempty<std::string> = {""};

View File

@ -5,7 +5,7 @@ functions that log or trace their execution. Something that, in an
imperative language, would likely be implemented by mutating some global imperative language, would likely be implemented by mutating some global
state, as in: state, as in:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
string logger; string logger;
bool negate(bool b) { bool negate(bool b) {
@ -25,7 +25,7 @@ have to pass the log explicitly, in and out. Let's do that by adding a
string argument, and pairing regular output with a string that contains string argument, and pairing regular output with a string that contains
the updated log: the updated log:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
pair<bool, string> negate(bool b, string logger) { pair<bool, string> negate(bool b, string logger) {
return make_pair(!b, logger + "Not so! "); return make_pair(!b, logger + "Not so! ");
} }
@ -60,7 +60,7 @@ continuous log is a separate concern. We still want the function to
produce a string, but we'd like to unburden it from producing a log. So produce a string, but we'd like to unburden it from producing a log. So
here's the compromise solution: here's the compromise solution:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
pair<bool, string> negate(bool b) { pair<bool, string> negate(bool b) {
return make_pair(!b, "Not so! "); return make_pair(!b, "Not so! ");
} }
@ -72,7 +72,7 @@ To see how this can be done, let's switch to a slightly more realistic
example. We have one function from string to string that turns lower example. We have one function from string to string that turns lower
case characters to upper case: case characters to upper case:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
string toUpper(string s) { string toUpper(string s) {
string result; string result;
int (*toupperp)(int) = &toupper; // toupper is overloaded int (*toupperp)(int) = &toupper; // toupper is overloaded
@ -83,14 +83,14 @@ string toUpper(string s) {
and another that splits a string into a vector of strings, breaking it and another that splits a string into a vector of strings, breaking it
on whitespace boundaries: on whitespace boundaries:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
vector<string> toWords(string s) { vector<string> toWords(string s) {
return words(s); return words(s);
} }
\end{Verbatim} \end{Verbatim}
The actual work is done in the auxiliary function \code{words}: The actual work is done in the auxiliary function \code{words}:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
vector<string> words(string s) { vector<string> words(string s) {
vector<string> result{""}; vector<string> result{""};
for (auto i = begin(s); i != end(s); ++i) for (auto i = begin(s); i != end(s); ++i)
@ -118,13 +118,13 @@ in a generic way by defining a template \code{Writer} that
encapsulates a pair whose first component is a value of arbitrary type encapsulates a pair whose first component is a value of arbitrary type
\code{A} and the second component is a string: \code{A} and the second component is a string:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class A> template<class A>
using Writer = pair<A, string>; using Writer = pair<A, string>;
\end{Verbatim} \end{Verbatim}
Here are the embellished functions: Here are the embellished functions:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
Writer<string> toUpper(string s) { Writer<string> toUpper(string s) {
string result; string result;
int (*toupperp)(int) = &toupper; int (*toupperp)(int) = &toupper;
@ -140,7 +140,7 @@ We want to compose these two functions into another embellished function
that uppercases a string and splits it into words, all the while that uppercases a string and splits it into words, all the while
producing a log of those actions. Here's how we may do it: producing a log of those actions. Here's how we may do it:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
Writer<vector<string>> process(string s) { Writer<vector<string>> process(string s) {
auto p1 = toUpper(s); auto p1 = toUpper(s);
auto p2 = toWords(p1.first); auto p2 = toWords(p1.first);
@ -174,7 +174,7 @@ important point is that this morphism is still considered an arrow
between the objects \code{int} and \code{bool}, even though the between the objects \code{int} and \code{bool}, even though the
embellished function returns a pair: embellished function returns a pair:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
pair<bool, string> isEven(int n) { pair<bool, string> isEven(int n) {
return make_pair(n % 2 == 0, "isEven "); return make_pair(n % 2 == 0, "isEven ");
} }
@ -184,7 +184,7 @@ with another morphism that goes from the object \code{bool} to
whatever. In particular, we should be able to compose it with our whatever. In particular, we should be able to compose it with our
earlier \code{negate}: earlier \code{negate}:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
pair<bool, string> negate(bool b) { pair<bool, string> negate(bool b) {
return make_pair(!b, "Not so! "); return make_pair(!b, "Not so! ");
} }
@ -193,7 +193,7 @@ Obviously, we cannot compose these two morphisms the same way we compose
regular functions, because of the input/output mismatch. Their regular functions, because of the input/output mismatch. Their
composition should look more like this: composition should look more like this:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
pair<bool, string> isOdd(int n) { pair<bool, string> isOdd(int n) {
pair<bool, string> p1 = isEven(n); pair<bool, string> p1 = isEven(n);
pair<bool, string> p2 = negate(p1.first); pair<bool, string> p2 = negate(p1.first);
@ -224,7 +224,7 @@ corresponding to three objects in our category. It should take two
embellished functions that are composable according to our rules, and embellished functions that are composable according to our rules, and
return a third embellished function: return a third embellished function:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class A, class B, class C> template<class A, class B, class C>
function<Writer<C>(A)> compose(function<Writer<B>(A)> m1, function<Writer<C>(A)> compose(function<Writer<B>(A)> m1,
function<Writer<C>(B)> m2) function<Writer<C>(B)> m2)
@ -249,7 +249,7 @@ There is still a lot of noise with the passing of types to the
C++14-compliant compiler that supports generalized lambda functions with C++14-compliant compiler that supports generalized lambda functions with
return type deduction (credit for this code goes to Eric Niebler): return type deduction (credit for this code goes to Eric Niebler):
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
auto const compose = [](auto m1, auto m2) { auto const compose = [](auto m1, auto m2) {
return [m1, m2](auto x) { return [m1, m2](auto x) {
auto p1 = m1(x); auto p1 = m1(x);
@ -261,7 +261,7 @@ auto const compose = [](auto m1, auto m2) {
In this new definition, the implementation of \code{process} In this new definition, the implementation of \code{process}
simplifies to: simplifies to:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
Writer<vector<string>> process(string s) { Writer<vector<string>> process(string s) {
return compose(toUpper, toWords)(s); return compose(toUpper, toWords)(s);
} }
@ -271,7 +271,7 @@ category, but what are the identity morphisms? These are not our regular
identity functions! They have to be morphisms from type A back to type identity functions! They have to be morphisms from type A back to type
A, which means they are embellished functions of the form: A, which means they are embellished functions of the form:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
Writer<A> identity(A); Writer<A> identity(A);
\end{Verbatim} \end{Verbatim}
They have to behave like units with respect to composition. If you look They have to behave like units with respect to composition. If you look
@ -279,7 +279,7 @@ at our definition of composition, you'll see that an identity morphism
should pass its argument without change, and only contribute an empty should pass its argument without change, and only contribute an empty
string to the log: string to the log:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class A> Writer<A> identity(A x) { template<class A> Writer<A> identity(A x) {
return make_pair(x, ""); return make_pair(x, "");
} }
@ -324,7 +324,7 @@ a -> Writer b
We'll declare the composition as a funny infix operator, sometimes We'll declare the composition as a funny infix operator, sometimes
called the ``fish'': called the ``fish'':
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
(>=>) :: (a -> Writer b) -> (b -> Writer c) -> (a -> Writer c) (>=>) :: (a -> Writer b) -> (b -> Writer c) -> (a -> Writer c)
\end{Verbatim} \end{Verbatim}
It's a function of two arguments, each being a function on its own, and It's a function of two arguments, each being a function on its own, and
@ -390,7 +390,7 @@ standard Prelude library.
Finally, the composition of the two functions is accomplished with the Finally, the composition of the two functions is accomplished with the
help of the fish operator: help of the fish operator:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
process :: String -> Writer [String] process :: String -> Writer [String]
process = upCase >=> toWords process = upCase >=> toWords
\end{Verbatim} \end{Verbatim}
@ -432,7 +432,7 @@ mathematical sense, so it doesn't fit the standard categorical mold. It
can, however, be represented by a function that returns an embellished can, however, be represented by a function that returns an embellished
type \code{optional}: type \code{optional}:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class A> class optional { template<class A> class optional {
bool _isValid; bool _isValid;
A _value; A _value;
@ -446,7 +446,7 @@ public:
As an example, here's the implementation of the embellished function As an example, here's the implementation of the embellished function
\code{safe\_root}: \code{safe\_root}:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
optional<double> safe_root(double x) { optional<double> safe_root(double x) {
if (x >= 0) return optional<double>{sqrt(x)}; if (x >= 0) return optional<double>{sqrt(x)};
else return optional<double>{}; else return optional<double>{};

View File

@ -265,7 +265,7 @@ snd (_, y) = y
\end{Verbatim} \end{Verbatim}
In C++, we would use template functions, for instance: In C++, we would use template functions, for instance:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class A, class B> A template<class A, class B> A
fst(pair<A, B> const & p) { fst(pair<A, B> const & p) {
return p.first; return p.first;
@ -359,7 +359,7 @@ equations are in natural numbers, and the dot is multiplication:
\emph{m} is a common factor shared by \emph{p'} and \emph{q'}. \emph{m} is a common factor shared by \emph{p'} and \emph{q'}.
Just to build some intuitions, let me show you that the pair Just to build some intuitions, let me show you that the pair
\code{(Int,\ Bool)} with the two canonical projections, \code{fst} \code{(Int, Bool)} with the two canonical projections, \code{fst}
and \code{snd} is indeed \emph{better} than the two candidates I and \code{snd} is indeed \emph{better} than the two candidates I
presented before. presented before.
@ -387,7 +387,7 @@ The \code{m} for the second example is similarly uniquely determined:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}[commandchars=\\\{\}]
m (x, _, b) = (x, b) m (x, _, b) = (x, b)
\end{Verbatim} \end{Verbatim}
We were able to show that \code{(Int,\ Bool)} is better than either of We were able to show that \code{(Int, Bool)} is better than either of
the two candidates. Let's see why the opposite is not true. Could we the two candidates. Let's see why the opposite is not true. Could we
find some \code{m'} that would help us reconstruct \code{fst} find some \code{m'} that would help us reconstruct \code{fst}
and \code{snd} from \code{p} and \code{q}? and \code{snd} from \code{p} and \code{q}?
@ -512,7 +512,7 @@ have to define a tag --- an enumeration --- and combine it with the
union. For instance, a tagged union of an \code{int} and a\\ union. For instance, a tagged union of an \code{int} and a\\
\code{char const *} could be implemented as: \code{char const *} could be implemented as:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
struct Contact { struct Contact {
enum { isPhone, isEmail } tag; enum { isPhone, isEmail } tag;
union { int phoneNum; char const * emailAddr; }; union { int phoneNum; char const * emailAddr; };
@ -522,7 +522,7 @@ The two injections can either be implemented as constructors or as
functions. For instance, here's the first injection as a function functions. For instance, here's the first injection as a function
\code{PhoneNum}: \code{PhoneNum}:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
Contact PhoneNum(int n) { Contact PhoneNum(int n) {
Contact c; Contact c;
c.tag = isPhone; c.tag = isPhone;
@ -673,7 +673,7 @@ isomorphism is the same as a bijection.
\section{Challenges}\label{challenges} \section{Challenges}\label{challenges}
\begin{enumerate} \begin{enumerate}
\tightlist \tightlist
\item \item
Show that the terminal object is unique up to unique isomorphism. Show that the terminal object is unique up to unique isomorphism.
\item \item
@ -688,14 +688,14 @@ isomorphism is the same as a bijection.
Show that \code{Either} is a ``better'' coproduct than \code{int} Show that \code{Either} is a ``better'' coproduct than \code{int}
equipped with two injections: equipped with two injections:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
int i(int n) { return n; } int i(int n) { return n; }
int j(bool b) { return b? 0: 1; } int j(bool b) { return b? 0: 1; }
\end{Verbatim} \end{Verbatim}
Hint: Define a function Hint: Define a function
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
int m(Either const & e); int m(Either const & e);
\end{Verbatim} \end{Verbatim}
@ -707,7 +707,7 @@ int m(Either const & e);
\item \item
Still continuing: What about these injections? Still continuing: What about these injections?
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
int i(int n) { int i(int n) {
if (n < 0) return n; if (n < 0) return n;
return n + 2; return n + 2;

View File

@ -25,8 +25,8 @@ Library.
\end{figure} \end{figure}
\noindent \noindent
Pairs are not strictly commutative: a pair \code{(Int,\ Bool)} cannot Pairs are not strictly commutative: a pair \code{(Int, Bool)} cannot
be substituted for a pair \code{(Bool,\ Int)}, even though they carry be substituted for a pair \code{(Bool, Int)}, even though they carry
the same information. They are, however, commutative up to isomorphism the same information. They are, however, commutative up to isomorphism
--- the isomorphism being given by the \code{swap} function (which is --- the isomorphism being given by the \code{swap} function (which is
its own inverse): its own inverse):
@ -114,7 +114,7 @@ can be defined alternatively as:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}[commandchars=\\\{\}]
data Pair a b = P a b data Pair a b = P a b
\end{Verbatim} \end{Verbatim}
Here, \code{Pair\ a\ b} is the name of the type paremeterized by two Here, \code{Pair a b} is the name of the type paremeterized by two
other types, \code{a} and \code{b}; and \code{P} is the name of other types, \code{a} and \code{b}; and \code{P} is the name of
the data constructor. You define a pair type by passing two types to the the data constructor. You define a pair type by passing two types to the
\code{Pair} type constructor. You construct a pair value by passing \code{Pair} type constructor. You construct a pair value by passing
@ -173,7 +173,7 @@ named fields is called a record in Haskell, and a \code{struct} in C.
Let's have a look at a simple example. We want to describe chemical Let's have a look at a simple example. We want to describe chemical
elements by combining two strings, name and symbol; and an integer, the elements by combining two strings, name and symbol; and an integer, the
atomic number; into one data structure. We can use a tuple atomic number; into one data structure. We can use a tuple
\code{(String,\ String,\ Int)} and remember which component represents \code{(String, String, Int)} and remember which component represents
what. We would extract components by pattern matching, as in this what. We would extract components by pattern matching, as in this
function that checks if the symbol of the element is the prefix of its function that checks if the symbol of the element is the prefix of its
name (as in \textbf{He} being the prefix of \textbf{Helium}): name (as in \textbf{He} being the prefix of \textbf{Helium}):
@ -185,7 +185,7 @@ startsWithSymbol (name, symbol, _) = isPrefixOf symbol name
This code is error prone, and is hard to read and maintain. It's much This code is error prone, and is hard to read and maintain. It's much
better to define a record: better to define a record:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
data Element = Element { name :: String data Element = Element { name :: String
, symbol :: String , symbol :: String
, atomicNumber :: Int } , atomicNumber :: Int }
@ -193,7 +193,7 @@ data Element = Element { name :: String
The two representations are isomorphic, as witnessed by these two The two representations are isomorphic, as witnessed by these two
conversion functions, which are the inverse of each other: conversion functions, which are the inverse of each other:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
tupleToElem :: (String, String, Int) -> Element tupleToElem :: (String, String, Int) -> Element
tupleToElem (n, s, a) = Element { name = n tupleToElem (n, s, a) = Element { name = n
, symbol = s , symbol = s
@ -242,7 +242,7 @@ And like pairs, \code{Either}s are commutative (up to isomorphism),
can be nested, and the nesting order is irrelevant (up to isomorphism). can be nested, and the nesting order is irrelevant (up to isomorphism).
So we can, for instance, define a sum equivalent of a triple: So we can, for instance, define a sum equivalent of a triple:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
data OneOfThree a b c = Sinistral a | Medial b | Dextral c data OneOfThree a b c = Sinistral a | Medial b | Dextral c
\end{Verbatim} \end{Verbatim}
and so on. and so on.
@ -279,7 +279,7 @@ data Color = Red | Green | Blue
\end{Verbatim} \end{Verbatim}
is the C++: is the C++:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
enum { Red, Green, Blue }; enum { Red, Green, Blue };
\end{Verbatim} \end{Verbatim}
An even simpler sum type: An even simpler sum type:
@ -328,7 +328,7 @@ List a = Nil | Cons a (List a)
can be translated to C++ using the null pointer trick to implement the can be translated to C++ using the null pointer trick to implement the
empty list: empty list:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class A> template<class A>
class List { class List {
Node<A> * _head; Node<A> * _head;
@ -380,7 +380,7 @@ the first constructor argument with a wildcard, because we are not
interested in it. The second argument to \code{Cons} is bound to the interested in it. The second argument to \code{Cons} is bound to the
variable \code{t} (I will call these things variables even though, variable \code{t} (I will call these things variables even though,
strictly speaking, they never vary: once bound to an expression, a strictly speaking, they never vary: once bound to an expression, a
variable never changes). The return value is \code{Just\ t}. Now, variable never changes). The return value is \code{Just t}. Now,
depending on how your \code{List} was created, it will match one of depending on how your \code{List} was created, it will match one of
the clauses. If it was created using \code{Cons}, the two arguments the clauses. If it was created using \code{Cons}, the two arguments
that were passed to it will be retrieved (and the first discarded). that were passed to it will be retrieved (and the first discarded).
@ -417,7 +417,7 @@ example, is it possible to create a pair of, say \code{Int} and
To create a pair you need two values. Although you can easily come up To create a pair you need two values. Although you can easily come up
with an integer, there is no value of type \code{Void}. Therefore, for with an integer, there is no value of type \code{Void}. Therefore, for
any type \code{a}, the type \code{(a,\ Void)} is uninhabited --- has any type \code{a}, the type \code{(a, Void)} is uninhabited --- has
no values --- and is therefore equivalent to \code{Void}. In other no values --- and is therefore equivalent to \code{Void}. In other
words, \code{a*0 = 0}. words, \code{a*0 = 0}.
@ -511,7 +511,7 @@ equation:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}[commandchars=\\\{\}]
List a = Nil | Cons a (List a) List a = Nil | Cons a (List a)
\end{Verbatim} \end{Verbatim}
If we do our usual substitutions, and also replace \code{List\ a} with If we do our usual substitutions, and also replace \code{List a} with
\code{x}, we get the equation: \code{x}, we get the equation:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}[commandchars=\\\{\}]
@ -613,7 +613,7 @@ circ (Rect d h) = 2.0 * (d + h)
have to touch in Haskell vs. C++ or Java? (Even if you're not a have to touch in Haskell vs. C++ or Java? (Even if you're not a
Haskell programmer, the modifications should be pretty obvious.) Haskell programmer, the modifications should be pretty obvious.)
\item \item
Show that \code{a\ +\ a\ =\ 2\ *\ a} holds for types (up to Show that \code{a + a = 2 * a} holds for types (up to
isomorphism). Remember that \code{2} corresponds to \code{Bool}, isomorphism). Remember that \code{2} corresponds to \code{Bool},
according to our translation table. according to our translation table.
\end{enumerate} \end{enumerate}

View File

@ -56,7 +56,7 @@ want all identity morphisms in C to be mapped to identity morphisms in
D: D:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}[commandchars=\\\{\}]
F ida = idF a F id\textsubscript{a} = id\textsubscript{F a}
\end{Verbatim} \end{Verbatim}
Here, \emph{id\textsubscript{a}} is the identity at the object \emph{a}, Here, \emph{id\textsubscript{a}} is the identity at the object \emph{a},
and \emph{id\textsubscript{F a}} the identity at \emph{F a}. and \emph{id\textsubscript{F a}} the identity at \emph{F a}.
@ -209,7 +209,7 @@ There are two cases to consider: \code{Nothing} and \code{Just}.
Here's the first case (I'm using Haskell pseudo-code to transform the Here's the first case (I'm using Haskell pseudo-code to transform the
left hand side to the right hand side): left hand side to the right hand side):
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
fmap id Nothing fmap id Nothing
= { definition of fmap } = { definition of fmap }
Nothing Nothing
@ -223,7 +223,7 @@ backwards. I replaced the expression \code{Nothing} with
in the middle --- here it was \code{Nothing}. The second case is also in the middle --- here it was \code{Nothing}. The second case is also
easy: easy:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
fmap id (Just x) fmap id (Just x)
= { definition of fmap } = { definition of fmap }
Just (id x) Just (id x)
@ -239,7 +239,7 @@ fmap (g . f) = fmap g . fmap f
\end{Verbatim} \end{Verbatim}
First the \code{Nothing} case: First the \code{Nothing} case:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
fmap (g . f) Nothing fmap (g . f) Nothing
= { definition of fmap } = { definition of fmap }
Nothing Nothing
@ -250,7 +250,7 @@ First the \code{Nothing} case:
\end{Verbatim} \end{Verbatim}
And then the \code{Just} case: And then the \code{Just} case:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
fmap (g . f) (Just x) fmap (g . f) (Just x)
= { definition of fmap } = { definition of fmap }
Just ((g . f) x) Just ((g . f) x)
@ -266,7 +266,7 @@ And then the \code{Just} case:
It's worth stressing that equational reasoning doesn't work for C++ It's worth stressing that equational reasoning doesn't work for C++
style ``functions'' with side effects. Consider this code: style ``functions'' with side effects. Consider this code:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
int square(int x) { int square(int x) {
return x * x; return x * x;
} }
@ -281,7 +281,7 @@ double y = square(counter());
Using equational reasoning, you would be able to inline \code{square} Using equational reasoning, you would be able to inline \code{square}
to get: to get:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
double y = counter() * counter(); double y = counter() * counter();
\end{Verbatim} \end{Verbatim}
This is definitely not a valid transformation, and it will not produce This is definitely not a valid transformation, and it will not produce
@ -299,7 +299,7 @@ implementation is much more complex, dealing with various ways the
argument may be passed, with copy semantics, and with the resource argument may be passed, with copy semantics, and with the resource
management issues characteristic of C++): management issues characteristic of C++):
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class T> template<class T>
class optional { class optional {
bool _isValid; // the tag bool _isValid; // the tag
@ -315,7 +315,7 @@ mapping of types. It maps any type \code{T} to a new type
\code{optional<T>}. Let's define its action on \code{optional<T>}. Let's define its action on
functions: functions:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class A, class B> template<class A, class B>
std::function<optional<B>(optional<A>)> std::function<optional<B>(optional<A>)>
fmap(std::function<B(A)> f) { fmap(std::function<B(A)> f) {
@ -330,7 +330,7 @@ fmap(std::function<B(A)> f) {
This is a higher order function, taking a function as an argument and This is a higher order function, taking a function as an argument and
returning a function. Here's the uncurried version of it: returning a function. Here's the uncurried version of it:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class A, class B> template<class A, class B>
optional<B> fmap(std::function<B(A)> f, optional<A> opt) { optional<B> fmap(std::function<B(A)> f, optional<A> opt) {
if (!opt.isValid()) if (!opt.isValid())
@ -428,7 +428,7 @@ template class, like \code{optional}, so by analogy, we would
parameterize \code{fmap} with a \newterm{template template parameter} parameterize \code{fmap} with a \newterm{template template parameter}
\code{F}. This is the syntax for it: \code{F}. This is the syntax for it:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<template<class> F, class A, class B> template<template<class> F, class A, class B>
F<B> fmap(std::function<B(A)>, F<A>); F<B> fmap(std::function<B(A)>, F<A>);
\end{Verbatim} \end{Verbatim}
@ -436,14 +436,14 @@ We would like to be able to specialize this template for different
functors. Unfortunately, there is a prohibition against partial functors. Unfortunately, there is a prohibition against partial
specialization of template functions in C++. You can't write: specialization of template functions in C++. You can't write:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class A, class B> template<class A, class B>
optional<B> fmap<optional>(std::function<B(A)> f, optional<A> opt) optional<B> fmap<optional>(std::function<B(A)> f, optional<A> opt)
\end{Verbatim} \end{Verbatim}
Instead, we have to fall back on function overloading, which brings us Instead, we have to fall back on function overloading, which brings us
back to the original definition of the uncurried \code{fmap}: back to the original definition of the uncurried \code{fmap}:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class A, class B> template<class A, class B>
optional<B> fmap(std::function<B(A)> f, optional<A> opt) { optional<B> fmap(std::function<B(A)> f, optional<A> opt) {
if (!opt.isValid()) if (!opt.isValid())
@ -514,7 +514,7 @@ If you are more comfortable with C++, consider the case of a
container. The implementation of \code{fmap} for \code{std::vector} container. The implementation of \code{fmap} for \code{std::vector}
is just a thin encapsulation of \code{std::transform}: is just a thin encapsulation of \code{std::transform}:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class A, class B> template<class A, class B>
std::vector<B> fmap(std::function<B(A)> f, std::vector<A> v) { std::vector<B> fmap(std::function<B(A)> f, std::vector<A> v) {
std::vector<B> w; std::vector<B> w;
@ -528,7 +528,7 @@ std::vector<B> fmap(std::function<B(A)> f, std::vector<A> v) {
We can use it, for instance, to square the elements of a sequence of We can use it, for instance, to square the elements of a sequence of
numbers: numbers:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
std::vector<int> v{ 1, 2, 3, 4 }; std::vector<int> v{ 1, 2, 3, 4 };
auto w = fmap([](int i) { return i*i; }, v); auto w = fmap([](int i) { return i*i; }, v);
std::copy( std::begin(w) std::copy( std::begin(w)
@ -691,7 +691,7 @@ This might be a little clearer in C++ (I never thought I would utter
those words!), where there is a stronger distinction between type those words!), where there is a stronger distinction between type
arguments --- which are compile-time --- and values, which are run-time: arguments --- which are compile-time --- and values, which are run-time:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class C, class A> template<class C, class A>
struct Const { struct Const {
Const(C v) : _v(v) {} Const(C v) : _v(v) {}
@ -702,7 +702,7 @@ The C++ implementation of \code{fmap} also ignores the function
argument and essentially re-casts the \code{Const} argument without argument and essentially re-casts the \code{Const} argument without
changing its value: changing its value:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class C, class A, class B> template<class C, class A, class B>
Const<C, B> fmap(std::function<B(A)> f, Const<C, A> c) { Const<C, B> fmap(std::function<B(A)> f, Const<C, A> c) {
return Const<C, B>{c._v}; return Const<C, B>{c._v};

View File

@ -249,7 +249,7 @@ arguments. The syntax is the same.
If you're getting a little lost, try applying \code{BiComp} to If you're getting a little lost, try applying \code{BiComp} to
\code{Either}, \code{Const ()}, \code{Identity}, \code{a}, and \code{Either}, \code{Const ()}, \code{Identity}, \code{a}, and
\code{b}, in this order. You will recover our bare-bone version of \code{b}, in this order. You will recover our bare-bone version of
\code{Maybe\ b} (\code{a} is ignored). \code{Maybe b} (\code{a} is ignored).
The new data type \code{BiComp} is a bifunctor in \code{a} and The new data type \code{BiComp} is a bifunctor in \code{a} and
\code{b}, but only if \code{bf} is itself a \code{Bifunctor} and \code{b}, but only if \code{bf} is itself a \code{Bifunctor} and
@ -260,11 +260,11 @@ know that there will be a definition of \code{bimap} available for
instance declaration: a set of class constraints followed by a double instance declaration: a set of class constraints followed by a double
arrow: arrow:
\begin{Verbatim}[commandchars=\\\{\}] \begin{minted}[breaklines]{text}
instance (Bifunctor bf, Functor fu, Functor gu) => instance (Bifunctor bf, Functor fu, Functor gu) =>
Bifunctor (BiComp bf fu gu) where Bifunctor (BiComp bf fu gu) where
bimap f1 f2 (BiComp x) = BiComp ((bimap (fmap f1) (fmap f2)) x) bimap f1 f2 (BiComp x) = BiComp ((bimap (fmap f1) (fmap f2)) x)
\end{Verbatim} \end{minted}
The implementation of \code{bimap} for \code{BiComp} is given in The implementation of \code{bimap} for \code{BiComp} is given in
terms of \code{bimap} for \code{bf} and the two \code{fmap}s for terms of \code{bimap} for \code{bf} and the two \code{fmap}s for
\code{fu} and \code{gu}. The compiler automatically infers all the \code{fu} and \code{gu}. The compiler automatically infers all the
@ -305,9 +305,9 @@ can't it be automated and performed by the compiler? Indeed, it can, and
it is. You need to enable a particular Haskell extension by including it is. You need to enable a particular Haskell extension by including
this line at the top of your source file: this line at the top of your source file:
\begin{Verbatim}[commandchars=\\\{\}] \begin{minted}{haskell}
{-# LANGUAGE DeriveFunctor #-} {-# LANGUAGE DeriveFunctor #-}
\end{Verbatim} \end{minted}
and then add \code{deriving Functor} to your data structure: and then add \code{deriving Functor} to your data structure:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}[commandchars=\\\{\}]
@ -334,7 +334,7 @@ is made into a generic template, you should be able to quickly implement
Let's have a look at a tree data structure, which we would define in Let's have a look at a tree data structure, which we would define in
Haskell as a recursive sum type: Haskell as a recursive sum type:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
data Tree a = Leaf a | Node (Tree a) (Tree a) data Tree a = Leaf a | Node (Tree a) (Tree a)
deriving Functor deriving Functor
\end{Verbatim} \end{Verbatim}
@ -353,7 +353,7 @@ The base class must define at least one virtual function in order to
support dynamic casting, so we'll make the destructor virtual (which is support dynamic casting, so we'll make the destructor virtual (which is
a good idea in any case): a good idea in any case):
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class T> template<class T>
struct Tree { struct Tree {
virtual ~Tree() {}; virtual ~Tree() {};
@ -361,7 +361,7 @@ struct Tree {
\end{Verbatim} \end{Verbatim}
The \code{Leaf} is just an \code{Identity} functor in disguise: The \code{Leaf} is just an \code{Identity} functor in disguise:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class T> template<class T>
struct Leaf : public Tree<T> { struct Leaf : public Tree<T> {
T _label; T _label;
@ -370,7 +370,7 @@ struct Leaf : public Tree<T> {
\end{Verbatim} \end{Verbatim}
The \code{Node} is a product type: The \code{Node} is a product type:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class T> template<class T>
struct Node : public Tree<T> { struct Node : public Tree<T> {
Tree<T> * _left; Tree<T> * _left;
@ -386,7 +386,7 @@ is treated like a bifunctor composed with two copies of the
analyzing code in these terms, but it's a good exercise in categorical analyzing code in these terms, but it's a good exercise in categorical
thinking. thinking.
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
template<class A, class B> template<class A, class B>
Tree<B> * fmap(std::function<B(A)> f, Tree<A> * t) { Tree<B> * fmap(std::function<B(A)> f, Tree<A> * t) {
Leaf<A> * pl = dynamic_cast <Leaf<A>*>(t); Leaf<A> * pl = dynamic_cast <Leaf<A>*>(t);
@ -405,7 +405,7 @@ issues, but in production code you would probably use smart pointers
Compare it with the Haskell implementation of \code{fmap}: Compare it with the Haskell implementation of \code{fmap}:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
instance Functor Tree where instance Functor Tree where
fmap f (Leaf a) = Leaf (f a) fmap f (Leaf a) = Leaf (f a)
fmap f (Node t t') = Node (fmap f t) (fmap f t') fmap f (Node t t') = Node (fmap f t) (fmap f t')
@ -467,7 +467,7 @@ So \code{id} will take \code{Writer a} and turn it into
\code{Writer a}. The fish operator will fish out the value of \code{Writer a}. The fish operator will fish out the value of
\code{a} and pass it as \code{x} to the lambda. There, \code{f} \code{a} and pass it as \code{x} to the lambda. There, \code{f}
will turn it into a \code{b} and \code{return} will embellish it, will turn it into a \code{b} and \code{return} will embellish it,
making it \code{Writer\ b}. Putting it all together, we end up with a making it \code{Writer b}. Putting it all together, we end up with a
function that takes \code{Writer a} and returns \code{Writer b}, function that takes \code{Writer a} and returns \code{Writer b},
exactly what \code{fmap} is supposed to produce. exactly what \code{fmap} is supposed to produce.
@ -479,7 +479,7 @@ every functor, though, gives rise to a Kleisli category.)
You might wonder if the \code{fmap} we have just defined is the same You might wonder if the \code{fmap} we have just defined is the same
\code{fmap} the compiler would have derived for us with \code{fmap} the compiler would have derived for us with
\code{deriving\ Functor}. Interestingly enough, it is. This is due to \code{deriving Functor}. Interestingly enough, it is. This is due to
the way Haskell implements polymorphic functions. It's called the way Haskell implements polymorphic functions. It's called
\newterm{parametric polymorphism}, and it's a source of so called \newterm{parametric polymorphism}, and it's a source of so called
\newterm{theorems for free}. One of those theorems says that, if there is \newterm{theorems for free}. One of those theorems says that, if there is
@ -577,13 +577,13 @@ by the way --- the kind we've been studying thus far --- are called
Here's the typeclass defining a contravariant functor (really, a Here's the typeclass defining a contravariant functor (really, a
contravariant \emph{endo}functor) in Haskell: contravariant \emph{endo}functor) in Haskell:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
class Contravariant f where class Contravariant f where
contramap :: (b -> a) -> (f a -> f b) contramap :: (b -> a) -> (f a -> f b)
\end{Verbatim} \end{Verbatim}
Our type constructor \code{Op} is an instance of it: Our type constructor \code{Op} is an instance of it:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
instance Contravariant (Op r) where instance Contravariant (Op r) where
-- (b -> a) -> Op r a -> Op r b -- (b -> a) -> Op r a -> Op r b
contramap f g = g . f contramap f g = g . f
@ -623,7 +623,7 @@ which is contra-functorial in the first argument and functorial in the
second. Here's the appropriate typeclass taken from the second. Here's the appropriate typeclass taken from the
\code{Data.Profunctor} library: \code{Data.Profunctor} library:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
class Profunctor p where class Profunctor p where
dimap :: (a -> b) -> (c -> d) -> p b c -> p a d dimap :: (a -> b) -> (c -> d) -> p b c -> p a d
dimap f g = lmap f . rmap g dimap f g = lmap f . rmap g
@ -649,7 +649,7 @@ the defaults for \code{lmap} and \code{rmap}, or implementing both
Now we can assert that the function-arrow operator is an instance of a Now we can assert that the function-arrow operator is an instance of a
\code{Profunctor}: \code{Profunctor}:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
instance Profunctor (->) where instance Profunctor (->) where
dimap ab cd bc = cd . bc . ab dimap ab cd bc = cd . bc . ab
lmap = flip (.) lmap = flip (.)
@ -677,7 +677,7 @@ data Pair a b = Pair a b
Show the isomorphism between the standard definition of \code{Maybe} Show the isomorphism between the standard definition of \code{Maybe}
and this desugaring: and this desugaring:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
type Maybe' a = Either (Const () a) (Identity a) type Maybe' a = Either (Const () a) (Identity a)
\end{Verbatim} \end{Verbatim}

View File

@ -1,7 +1,7 @@
\lettrine[lhang=0.17]{S}{o far I've} been glossing over the meaning of function types. A function \lettrine[lhang=0.17]{S}{o far I've} been glossing over the meaning of function types. A function
type is different from other types. type is different from other types.
\begin{wrapfigure}[13]{R}{0pt} \begin{wrapfigure}[12]{R}{0pt}
\raisebox{0pt}[\dimexpr\height-0.75\baselineskip\relax]{ \raisebox{0pt}[\dimexpr\height-0.75\baselineskip\relax]{
\fbox{\includegraphics[width=40mm]{images/set-hom-set.jpg}}}% \fbox{\includegraphics[width=40mm]{images/set-hom-set.jpg}}}%
\caption{Hom-set in Set is just a set} \caption{Hom-set in Set is just a set}
@ -322,14 +322,14 @@ initializer lists).
You can partially apply a C++ function using the template You can partially apply a C++ function using the template
\code{std::bind}. For instance, given a function of two strings: \code{std::bind}. For instance, given a function of two strings:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
std::string catstr(std::string s1, std::string s2) { std::string catstr(std::string s1, std::string s2) {
return s1 + s2; return s1 + s2;
} }
\end{Verbatim} \end{Verbatim}
you can define a function of one string: you can define a function of one string:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
using namespace std::placeholders; using namespace std::placeholders;
auto greet = std::bind(catstr, "Hello ", _1); auto greet = std::bind(catstr, "Hello ", _1);
@ -339,7 +339,7 @@ Scala, which is more functional than C++ or Java, falls somewhere in
between. If you anticipate that the function you're defining will be between. If you anticipate that the function you're defining will be
partially applied, you define it with multiple argument lists: partially applied, you define it with multiple argument lists:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
def catstr(s1: String)(s2: String) = s1 + s2 def catstr(s1: String)(s2: String) = s1 + s2
\end{Verbatim} \end{Verbatim}
Of course that requires some amount of foresight or prescience on the Of course that requires some amount of foresight or prescience on the

View File

@ -52,7 +52,7 @@ directly from function to function. We also inline short segments of
glue code rather than abstract them into helper functions. Here's an glue code rather than abstract them into helper functions. Here's an
imperative-style implementation of the vector-length function in C: imperative-style implementation of the vector-length function in C:
\begin{Verbatim}[commandchars=\\\{\}] \begin{Verbatim}
double vlen(double * v) { double vlen(double * v) {
double d = 0.0; double d = 0.0;
int n; int n;