Sha256: a4cbdaec33ba3b4c672b52bea67c3b1935a1478750d3c7b3e7604e9cf8a58b71

Contents?: true

Size: 1.79 KB

Versions: 19

Compression:

Stored size: 1.79 KB

Contents

module DidYouMean
  module Jaro
    module_function

    def distance(str1, str2)
      str1, str2 = str2, str1 if str1.length > str2.length
      length1, length2 = str1.length, str2.length

      m          = 0.0
      t          = 0.0
      range      = (length2 / 2).floor - 1
      range      = 0 if range < 0
      flags1     = 0
      flags2     = 0

      # Avoid duplicating enumerable objects
      str1_codepoints = str1.codepoints
      str2_codepoints = str2.codepoints

      i = 0
      while i < length1
        last = i + range
        j    = (i >= range) ? i - range : 0

        while j <= last
          if flags2[j] == 0 && str1_codepoints[i] == str2_codepoints[j]
            flags2 |= (1 << j)
            flags1 |= (1 << i)
            m += 1
            break
          end

          j += 1
        end

        i += 1
      end

      k = i = 0
      while i < length1
        if flags1[i] != 0
          j = index = k

          k = while j < length2
            index = j
            break(j + 1) if flags2[j] != 0

            j += 1
          end

          t += 1 if str1_codepoints[i] != str2_codepoints[index]
        end

        i += 1
      end
      t = (t / 2).floor

      m == 0 ? 0 : (m / length1 + m / length2 + (m - t) / m) / 3
    end
  end

  module JaroWinkler
    WEIGHT    = 0.1
    THRESHOLD = 0.7

    module_function

    def distance(str1, str2)
      jaro_distance = Jaro.distance(str1, str2)

      if jaro_distance > THRESHOLD
        codepoints2  = str2.codepoints
        prefix_bonus = 0

        i = 0
        str1.each_codepoint do |char1|
          char1 == codepoints2[i] && i < 4 ? prefix_bonus += 1 : break
          i += 1
        end

        jaro_distance + (prefix_bonus * WEIGHT * (1 - jaro_distance))
      else
        jaro_distance
      end
    end
  end
end

Version data entries

19 entries across 19 versions & 2 rubygems

Version Path
did_you_mean-1.6.3 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.6.2 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.6.1 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.5.0 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.4.0 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.3.1 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.2.2 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.1.3 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.0.4 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.3.0 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.2.1 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.2.0 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.0.3 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.1.2 lib/did_you_mean/jaro_winkler.rb
ruby-compiler-0.1.1 vendor/ruby/gems/did_you_mean-1.1.0/lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.1.0 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.0.2 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.0.1 lib/did_you_mean/jaro_winkler.rb
did_you_mean-1.0.0 lib/did_you_mean/jaro_winkler.rb