zf

zenflows testing
git clone https://s.sonu.ch/~srfsh/zf.git
Log | Files | Refs | Submodules | README | LICENSE

append_single_item.ex (1512B)


      1 defmodule Credo.Check.Refactor.AppendSingleItem do
      2   use Credo.Check,
      3     base_priority: :low,
      4     tags: [:controversial],
      5     explanations: [
      6       check: """
      7       When building up large lists, it is faster to prepend than
      8       append. Therefore: It is sometimes best to prepend to the list
      9       during iteration and call Enum.reverse/1 at the end, as it is quite
     10       fast.
     11 
     12       Example:
     13 
     14           list = list_so_far ++ [new_item]
     15 
     16           # refactoring it like this can make the code faster:
     17 
     18           list = [new_item] ++ list_so_far
     19           # ...
     20           Enum.reverse(list)
     21 
     22       """
     23     ]
     24 
     25   @doc false
     26   @impl true
     27   def run(%SourceFile{} = source_file, params) do
     28     issue_meta = IssueMeta.for(source_file, params)
     29 
     30     Credo.Code.prewalk(source_file, &traverse(&1, &2, issue_meta))
     31   end
     32 
     33   # [a] ++ b is OK
     34   # TODO: consider for experimental check front-loader (ast)
     35   defp traverse({:++, _, [[_], _]} = ast, issues, _issue_meta) do
     36     {ast, issues}
     37   end
     38 
     39   # a ++ [b] is not
     40   defp traverse({:++, meta, [_, [_]]} = ast, issues, issue_meta) do
     41     {ast, [issue_for(issue_meta, meta[:line], :++) | issues]}
     42   end
     43 
     44   defp traverse(ast, issues, _issue_meta) do
     45     {ast, issues}
     46   end
     47 
     48   defp issue_for(issue_meta, line_no, trigger) do
     49     format_issue(
     50       issue_meta,
     51       message: "Appending a single item to a list is inefficient, use [head | tail]
     52                 notation (and Enum.reverse/1 when order matters)",
     53       trigger: trigger,
     54       line_no: line_no
     55     )
     56   end
     57 end