 
   Any protocol module contains three extra functions:
 
-
     * `__protocol__/1` - returns the protocol name when `:name` is given, and a
-      keyword list with the protocol functions when `:functions` is given
+      keyword list with the protocol functions and their arities when
+      `:functions` is given
 
     * `impl_for/1` - receives a structure and returns the module that
       implements the protocol for the structure, `nil` otherwise
 
     * `impl_for!/1` - same as above but raises an error if an implementation is
       not found
+
+      Enumerable.__protocol__(:functions)
+      #=> [count: 1, member?: 2, reduce: 3]
+
+      Enumerable.impl_for([])
+      #=> Enumerable.List
+
+      Enumerable.impl_for(42)
+      #=> nil
 
   ## Consolidation
 

  Defines an exception.

  Exceptions are structs backed by a module that implements
  the Exception behaviour. The Exception behaviour requires
  two functions to be implemented:

    * `exception/1` - that receives the arguments given to `raise/2`
       and returns the exception struct. The default implementation
       accepts a set of keyword arguments that is merged into the
       struct.

    * `message/1` - receives the exception struct and must return its
      message. Most commonly exceptions have a message field which
      by default is accessed by this function. However, if your exception
      does not have a message field, this function must be explicitly
      implemented.

  Since exceptions are structs, all the API supported by `defstruct/1`
  is also available in `defexception/1`.

  ## Raising exceptions

  The most common way to raise an exception is via the `raise/2`
  function:

      defmodule MyAppError do
        defexception [:message]

        defstruct name: nil, age: nil
      end

  Struct fields are evaluated at compile-time, which allows
  them to be dynamic. In the example below, `10 + 11` is
  evaluated at compile-time and the age field is stored
  with value `21`:

      defmodule User do
