longest_common_prefix.sf 1.0 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950
  1. #!/usr/bin/ruby
  2. #
  3. ## https://rosettacode.org/wiki/Longest_common_prefix
  4. #
  5. # Finds the first point where the tree bifurcates
  6. func find_common_prefix(hash, acc) {
  7. if ((var keys = hash.keys).len == 1) {
  8. return __FUNC__(hash{keys[0]}, acc+keys[0])
  9. }
  10. return acc;
  11. }
  12. # Creates a tree like: {a => {b => {c => {}}}}
  13. func lcp(*strings) {
  14. var hash = Hash()
  15. strings.sort_by{.len}.each { |str|
  16. var ref = hash
  17. str.is_empty && return ''
  18. str.each { |char|
  19. if (ref.has_key(char)) {
  20. ref = ref{char}
  21. ref.keys.len == 0 && break
  22. } else {
  23. ref = (ref{char} = Hash())
  24. }
  25. };
  26. };
  27. return find_common_prefix(hash, '')
  28. }
  29. var data = [
  30. ["interspecies","interstellar","interstate"],
  31. ["throne","throne"],
  32. ["throne","dungeon"],
  33. ["throne","","throne"],
  34. ["cheese"],
  35. [""],
  36. [],
  37. ["prefix","suffix"],
  38. ["foo","foobar"]
  39. ]
  40. data.each { |set|
  41. say "lcp(#{set.dump.substr(1,-1)}) = #{lcp(set...).dump}"
  42. }