fuzzyStringMatch.js.flow 1.1 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849
  1. import _ from 'lodash';
  2. // Creates an array of letter pairs from a given array
  3. // origin: https://github.com/d3/d3-array/blob/master/src/pairs.js
  4. const arrayPairs = (array) => {
  5. let ii = 0;
  6. const length = array.length - 1;
  7. let letter = array[0];
  8. const pairs = Array.from({ length: length < 0 ? 0 : length });
  9. while (ii < length) {
  10. // Not entirely sure what ++ii does yet
  11. // eslint-disable-next-line no-plusplus
  12. pairs[ii] = [letter, letter = array[++ii]];
  13. }
  14. return pairs;
  15. };
  16. // Based on http://stackoverflow.com/a/23305385
  17. const stringSimilarity = (str1, str2) => {
  18. if (str1.length > 0 && str2.length > 0) {
  19. const pairs1 = arrayPairs(str1);
  20. const pairs2 = arrayPairs(str2);
  21. const unionLen = pairs1.length + pairs2.length;
  22. let hitCount;
  23. hitCount = 0;
  24. _.forIn(pairs1, (val1) => {
  25. _.forIn(pairs2, (val2) => {
  26. if (_.isEqual(val1, val2)) {
  27. hitCount += 1;
  28. }
  29. });
  30. });
  31. if (hitCount > 0) {
  32. return (2 * hitCount) / unionLen;
  33. }
  34. }
  35. return 0;
  36. };
  37. export default (needle, haystack, weight = 0.5) => (
  38. stringSimilarity(needle, haystack) >= Number(weight)
  39. );