Module: Ferret::Utils::NumberTools

Defined in:
lib/ferret/utils/number_tools.rb

Overview

Provides support for converting longs to Strings, and back again. The strings are structured so that lexicographic sorting order is preserved.

That is, if long1 is less than long2 for any two longs long1 and long2, then NumberTools.long_to_s(long1) is lexicographically less than NumberTools.long_to_s(long2). (Similarly for “greater than” and “equals”.)

This class handles all long values

Constant Summary collapse

RADIX =
36
NEGATIVE_PREFIX =
'-'
POSITIVE_PREFIX =

NB: NEGATIVE_PREFIX must be < POSITIVE_PREFIX

'0'
LONG_MAX_VALUE =

The following constants are from Java

9223372036854775807
LONG_MIN_VALUE =
-9223372036854775808
MIN_STRING_VALUE =

NB: This function is used to match the java equivalent. Actually ruby allows much larger numbers than Java so this is just so that we can read the Java Lucene created indexes.

NEGATIVE_PREFIX + "0000000000000"
MAX_STRING_VALUE =
POSITIVE_PREFIX + "1y2p0ij32e8e7"
STR_SIZE =

The length of the long field

MIN_STRING_VALUE.length()

Class Method Summary collapse

Class Method Details

.long_to_s(l) ⇒ Object

Converts a long to a String suitable for indexing.



37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
# File 'lib/ferret/utils/number_tools.rb', line 37

def NumberTools.long_to_s(l)
  if (l == LONG_MIN_VALUE)
      # special case, because long is not symetric around zero
      return MIN_STRING_VALUE;
  end

  s = ""
  if (l < 0)
    s << NEGATIVE_PREFIX
    l = LONG_MAX_VALUE + l + 1
  else
    s << POSITIVE_PREFIX
  end
  num = l.to_s(RADIX)

  pad_len = STR_SIZE - num.length() - s.length()
  while ((pad_len -= 1) >= 0)
      s << '0'
  end
  s << num

  return s
end

.s_to_long(s) ⇒ Object

Converts a String that was returned by #long_to_s back to a long.

Throws

ArgumentError if the input is nil



64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
# File 'lib/ferret/utils/number_tools.rb', line 64

def NumberTools.s_to_long(s)
  if (s == nil)
    raise ArgumentError, "string cannot be nil"
  end
  if (s.length() != STR_SIZE)
    raise ArgumentError, "string is the wrong size"
  end

  if (s == MIN_STRING_VALUE)
    return LONG_MIN_VALUE
  end

  prefix = s[0,1]
  l = s[1..-1].to_i(36)

  if (prefix == POSITIVE_PREFIX)
      # nop
  elsif (prefix == NEGATIVE_PREFIX)
      l = l - LONG_MAX_VALUE - 1
  else
    raise ArgumentError, "string <" + prefix +
      "> does not begin with the correct prefix"
  end

  return l
end