anchor.diff:          false -> false
       end;
   dyn_record(_V) -> false.
  -
  -%% string classifier functions
  -is_str_integer(S) -> string_in_ranges(S, [{$0, $9}]).
  -is_str_alpha(S) -> string_in_ranges(S, [{$A, $Z}, {$a, $z}]).
  -is_str_alnum(S) -> string_in_ranges(S, [{$0, $9}, {$A, $Z}, {$a, $z}]).
  -is_str_printable(S) -> string_in_ranges(S, [$\r, $\n, $\t, {32, 126}, {160, 255}]).
  -
  -%% check that string consists of chars that fit in the given ranges
  -string_in_ranges([],_Ranges)   -> true;
  -string_in_ranges([C|L], Ranges) ->
  -    case char_in_ranges(C, Ranges) of
  -        false -> false;
  -        true  -> string_in_ranges(L, Ranges)
  -    end.
  -
  -%% check that char C is in one of the ranges spec'd as [{Min, Max}|Char].
  -char_in_ranges(_C, []) -> false;
  -char_in_ranges(C, [{Min, Max} | _]) when C >= Min, C =< Max -> true;
  -char_in_ranges(C, [{_Min,_Max} | Rest]) -> char_in_ranges(C, Rest);
  -char_in_ranges(C, [C | _]) -> true;
  -char_in_ranges(C, [_Char | Rest]) -> char_in_ranges(C, Rest).
  -
  -%% order of magnitude for integers and floats
  -mag(X, N) -> trunc(math:log10(abs(X))) div N * N.
   
   
   %% class-specific extra data
  
positive.code:     end;
  
  subtype(M, map) -> subtype_map(M);
  
  subtype(S, str_printable) ->
      case is_str_alnum(S) of
          true -> str_alnum;
          false ->
              case ds_opts:getopt(strlen) of
                  true -> {str_printable, {len, length(S)}};
                  false -> '$null'
              end
      end;
  
  subtype(S, str_alnum) ->
      case is_str_integer(S) of
          true -> str_integer;
          false ->
              case is_str_alpha(S) of
                  true -> str_alpha;
                  false ->
                      case ds_opts:getopt(strlen) of
                          true -> {str_alnum, {len, length(S)}};
                          false -> '$null'
                      end
              end
      end;
  
  subtype(S, str_integer) ->
      case ds_opts:getopt(strlen) of
          true -> {str_integer, {len, length(S)}};
          false -> '$null'
      end;
  
  subtype(S, str_alpha) ->
      case ds_opts:getopt(strlen) of
          true -> {str_alpha, {len, length(S)}};
          false -> '$null'
      end;
  
  %% compound types where we want to recurse on their elements:
  subtype(T, {tuple,_N}) -> {'$fields', tuple_to_list(T)};
  
negative.code: %% Tests
  -ifdef(TEST).
  
  -endif.
  