iixr

Changeset

102:ac0167b6ed9b
2011-09-30 Paul Boddie raw files shortlog changelog graph Added comments and docstrings. default tip
iixr/data.py (file)
     1.1 --- a/iixr/data.py	Tue Feb 15 00:13:21 2011 +0100
     1.2 +++ b/iixr/data.py	Fri Sep 30 00:41:34 2011 +0200
     1.3 @@ -23,7 +23,18 @@
     1.4  
     1.5  # High-level representations.
     1.6  
     1.7 -def convert_sequence(values, op, last_from_old):
     1.8 +def convert_sequence(values, op, last_from_preceding):
     1.9 +
    1.10 +    """
    1.11 +    Convert the given sequence of 'values' either to a sequence of delta values
    1.12 +    if 'op' is a subtractor of some kind, using the preceding value in the
    1.13 +    sequence as the basis of the calculation of a delta for the current value
    1.14 +    (with 'last_from_preceding' set to a true value), or from a sequence of
    1.15 +    delta values if 'op' is an adder of some kind, using the last result as the
    1.16 +    basis of the calculation of an absolute value (with 'last_from_preceding'
    1.17 +    set to a false value).
    1.18 +    """
    1.19 +
    1.20      if values:
    1.21          new_values = list(values)
    1.22          last = new_values[0]
    1.23 @@ -36,7 +47,7 @@
    1.24              # Subtracting entries requires the old value to be used.
    1.25              # Adding entries requires the new value.
    1.26  
    1.27 -            if last_from_old:
    1.28 +            if last_from_preceding:
    1.29                  last = current
    1.30              else:
    1.31                  last = new_values[i]
    1.32 @@ -47,6 +58,13 @@
    1.33      else:
    1.34          return values
    1.35  
    1.36 +# Monotonic operators where an input sequence must always, when combined with an
    1.37 +# operand, produce a result whose elements are all greater than or equal to the
    1.38 +# values of the input sequence (for addition) or all less than or equal to the
    1.39 +# values of the input sequence (for subtraction).
    1.40 +#
    1.41 +# For example: (1, 2) -> (2, 2) -> (2, 3) -> (3, 4)
    1.42 +
    1.43  def op_seq_monotonic(x, y, op):
    1.44      return tuple([op(a, b) for a, b in zip(x, y)])
    1.45  
    1.46 @@ -56,37 +74,66 @@
    1.47  def sub_seq_monotonic(x, y):
    1.48      return op_seq_monotonic(x, y, operator.sub)
    1.49  
    1.50 -def add_seq(x, y):
    1.51 -    length = min(len(x), len(y))
    1.52 -    seq = list(x)[:length]
    1.53 +# Operators where an input sequence, when combined with an operand, may produce
    1.54 +# a result whose elements generally obey the properties for a monotonic sequence
    1.55 +# as described above, but where an element in the result may be reset with
    1.56 +# respect to the corresponding element in the input sequence and be less than
    1.57 +# that element (for addition) or greater than that element (for subtraction).
    1.58 +#
    1.59 +# For example: (1, 2) -> (2, 0) -> (2, 3) -> (3, 1)
    1.60 +
    1.61 +def add_seq(delta, input):
    1.62 +
    1.63 +    "Add 'delta' to 'input'."
    1.64 +
    1.65 +    length = min(len(delta), len(input))
    1.66 +    seq = list(delta)[:length]
    1.67      i = 0
    1.68      while i < length:
    1.69 -        if x[i] != 0:
    1.70 -            seq[i] = x[i] + y[i]
    1.71 +
    1.72 +        # If the delta is not zero, apply it to the input and retain the rest of
    1.73 +        # the delta sequence as absolute values in the result.
    1.74 +
    1.75 +        if delta[i] != 0:
    1.76 +            seq[i] = delta[i] + input[i]
    1.77              break
    1.78 -        seq[i] = y[i]
    1.79 +
    1.80 +        seq[i] = input[i]
    1.81          i += 1
    1.82      return tuple(seq)
    1.83  
    1.84 -def sub_seq(x, y):
    1.85 -    length = min(len(x), len(y))
    1.86 -    seq = list(x)[:length]
    1.87 +def sub_seq(current, last):
    1.88 +
    1.89 +    "Subtract 'current' from 'last'."
    1.90 +
    1.91 +    length = min(len(current), len(last))
    1.92 +    seq = list(current)[:length]
    1.93      i = 0
    1.94      while i < length:
    1.95 -        replacement = x[i] - y[i]
    1.96 +
    1.97 +        # Calculate a suitable delta value. If it is not zero, record it and
    1.98 +        # retain the rest of the current value to reset the sequence in the
    1.99 +        # result.
   1.100 +
   1.101 +        replacement = current[i] - last[i]
   1.102          if replacement != 0:
   1.103              seq[i] = replacement
   1.104              break
   1.105 +
   1.106          seq[i] = 0
   1.107          i += 1
   1.108      return tuple(seq)
   1.109  
   1.110 +# Data inspection functions.
   1.111 +
   1.112  def is_sequence(value):
   1.113      return isinstance(value, (list, tuple))
   1.114  
   1.115  def sizeof(value):
   1.116      return is_sequence(value) and len(value) or 0
   1.117  
   1.118 +# Functions returning operators appropriate for the given structure size.
   1.119 +
   1.120  def get_monotonic_adder(size):
   1.121      return size and add_seq_monotonic or operator.add
   1.122