 
   Typically called after formatting when the data cannot be printed.
   """
-  @spec prune(IO.chardata) :: IO.chardata
+  @spec prune(IO.chardata()) :: IO.chardata()
   def prune(binary) when is_binary(binary), do: prune_binary(binary, "")
-  def prune([h | t]) when h in 0..1114111, do: [h | prune(t)]
+  def prune([h | t]) when h in 0..1_114_111, do: [h | prune(t)]
   def prune([h | t]), do: [prune(h) | prune(t)]
   def prune([]), do: []
   def prune(_), do: @replacement
 
-  defp prune_binary(<<h::utf8, t::binary>>, acc),
-    do: prune_binary(t, <<acc::binary, h::utf8>>)
-  defp prune_binary(<<_, t::binary>>, acc),
-    do: prune_binary(t, <<acc::binary, @replacement>>)
-  defp prune_binary(<<>>, acc),
-    do: acc
+  defp prune_binary(<<h::utf8, t::binary>>, acc), do: prune_binary(t, <<acc::binary, h::utf8>>)
+  defp prune_binary(<<_, t::binary>>, acc), do: prune_binary(t, <<acc::binary, @replacement>>)
+  defp prune_binary(<<>>, acc), do: acc
 
   @doc ~S"""
   Compiles a format string into a data structure that the `format/5` can handle.

    for part <- Regex.split(regex, str, on: [:head, :tail], trim: true) do
      case part do
        "$" <> code -> compile_code(String.to_atom(code))
        _           -> part
      end
    end
  end

  defp compile_code(key) when key in @valid_patterns, do: key
  defp compile_code(key) when is_atom(key) do
    raise(ArgumentError, message: "$#{key} is an invalid format pattern.")
  end

  @doc """

    [Integer.to_string(yy), ?-, pad2(mm), ?-, pad2(dd)]
  end

  defp pad3(int) when int < 10, do: [?0, ?0, Integer.to_string(int)]
  defp pad3(int) when int < 100, do: [?0, Integer.to_string(int)]
  defp pad3(int), do: Integer.to_string(int)

