Your max implementation will give a wrong answer if your
list consists of negative numbers.
At the cost of (sometimes) passing one extra argument,
reduce makes it easy to handle whatever initialization
logic may be useful. As the example of max shows, this
is not an advantage to be sneezed at.