nodes: 0, module; 1, function_definition; 2, function_name:split; 3, parameters; 4, comment:# pylint: disable=g-doc-args; 5, block; 6, identifier:cls; 7, identifier:n; 8, identifier:contiguous; 9, default_parameter; 10, default_parameter; 11, expression_statement; 12, if_statement; 13, expression_statement; 14, if_statement; 15, expression_statement; 16, while_statement; 17, expression_statement; 18, if_statement; 19, identifier:can_query; 20, attribute; 21, identifier:_app; 22, None; 23, comment:"""Splits the complete NamespaceRange into n equally-sized NamespaceRanges.
  
      Args:
        n: The maximum number of NamespaceRanges to return. Fewer than n
            namespaces may be returned.
        contiguous: If True then the returned NamespaceRanges will cover the
            entire space of possible namespaces (i.e. from MIN_NAMESPACE to
            MAX_NAMESPACE) without gaps. If False then the returned
            NamespaceRanges may exclude namespaces that don't appear in the
            datastore.
        can_query: A function that returns True if split() can query the datastore
            to generate more fair namespace range splits, and False otherwise.
            If not set then split() is allowed to make 50 datastore queries.
  
      Returns:
        A list of at most n NamespaceRanges representing a near-equal distribution
        of actual existant datastore namespaces. The returned list will be sorted
        lexographically.
  
      Raises:
        ValueError: if n is < 1.
      """; 24, comparison_operator:n < 1; 25, block; 26, assignment; 27, call; 28, block; 29, else_clause; 30, assignment; 31, boolean_operator; 32, block; 33, assignment; 34, identifier:contiguous; 35, block; 36, else_clause; 37, call; 38, identifier:next; 39, identifier:n; 40, integer:1; 41, raise_statement; 42, identifier:ranges; 43, None; 44, identifier:can_query; 45, argument_list; 46, if_statement; 47, block; 48, identifier:singles; 49, list; 50, identifier:ranges; 51, comparison_operator:(len(ranges) + len(singles)) < n; 52, expression_statement; 53, if_statement; 54, identifier:ns_ranges; 55, call; 56, if_statement; 57, expression_statement; 58, for_statement; 59, return_statement; 60, block; 61, attribute; 62, argument_list; 63, call; 64, not_operator; 65, block; 66, else_clause; 67, expression_statement; 68, parenthesized_expression; 69, identifier:n; 70, assignment; 71, attribute; 72, block; 73, else_clause; 74, identifier:sorted; 75, argument_list; 76, not_operator; 77, comment:# This condition is possible if every namespace was deleted after the; 78, comment:# first call to ns_range.normalized_start().; 79, block; 80, assignment; 81, identifier:i; 82, call; 83, block; 84, identifier:continuous_ns_ranges; 85, return_statement; 86, identifier:itertools; 87, identifier:chain; 88, call; 89, call; 90, identifier:ValueError; 91, argument_list; 92, identifier:contiguous; 93, expression_statement; 94, if_statement; 95, block; 96, assignment; 97, binary_operator:len(ranges) + len(singles); 98, identifier:namespace_range; 99, call; 100, identifier:namespace_range; 101, identifier:is_single_namespace; 102, expression_statement; 103, block; 104, binary_operator:singles + ranges; 105, keyword_argument; 106, identifier:ns_ranges; 107, return_statement; 108, identifier:continuous_ns_ranges; 109, list; 110, identifier:range; 111, argument_list; 112, if_statement; 113, if_statement; 114, expression_statement; 115, identifier:ns_ranges; 116, attribute; 117, argument_list; 118, attribute; 119, argument_list; 120, string; 121, assignment; 122, not_operator; 123, block; 124, else_clause; 125, expression_statement; 126, if_statement; 127, expression_statement; 128, identifier:ranges; 129, list; 130, call; 131, call; 132, attribute; 133, argument_list; 134, call; 135, expression_statement; 136, if_statement; 137, if_statement; 138, expression_statement; 139, identifier:singles; 140, identifier:ranges; 141, identifier:key; 142, lambda; 143, list; 144, call; 145, comparison_operator:i == 0; 146, block; 147, else_clause; 148, comparison_operator:i == len(ns_ranges) - 1; 149, block; 150, else_clause; 151, call; 152, identifier:itertools; 153, identifier:repeat; 154, True; 155, integer:50; 156, identifier:itertools; 157, identifier:repeat; 158, False; 159, string_content:n must be >= 1; 160, identifier:ns_keys; 161, call; 162, identifier:ns_keys; 163, return_statement; 164, block; 165, assignment; 166, comparison_operator:ns_range is None; 167, block; 168, assignment; 169, call; 170, identifier:len; 171, argument_list; 172, identifier:len; 173, argument_list; 174, identifier:ranges; 175, identifier:pop; 176, integer:0; 177, attribute; 178, argument_list; 179, assignment; 180, call; 181, block; 182, comparison_operator:right is not None; 183, block; 184, call; 185, lambda_parameters; 186, attribute; 187, call; 188, identifier:len; 189, argument_list; 190, identifier:i; 191, integer:0; 192, expression_statement; 193, block; 194, identifier:i; 195, binary_operator:len(ns_ranges) - 1; 196, expression_statement; 197, block; 198, attribute; 199, argument_list; 200, identifier:get_namespace_keys; 201, argument_list; 202, list; 203, if_statement; 204, comment:# Use the first key and save the initial normalized_start() call.; 205, expression_statement; 206, identifier:ns_range; 207, call; 208, identifier:ns_range; 209, None; 210, return_statement; 211, identifier:ranges; 212, list; 213, identifier:NamespaceRange; 214, argument_list; 215, identifier:ranges; 216, identifier:singles; 217, identifier:singles; 218, identifier:append; 219, identifier:namespace_range; 220, pattern_list; 221, call; 222, identifier:can_query; 223, argument_list; 224, expression_statement; 225, identifier:right; 226, None; 227, expression_statement; 228, attribute; 229, argument_list; 230, identifier:ns_range; 231, identifier:ns_range; 232, identifier:namespace_start; 233, identifier:NamespaceRange; 234, argument_list; 235, identifier:ns_ranges; 236, assignment; 237, expression_statement; 238, call; 239, integer:1; 240, assignment; 241, expression_statement; 242, identifier:continuous_ns_ranges; 243, identifier:append; 244, call; 245, identifier:_app; 246, binary_operator:n + 1; 247, comparison_operator:len(ns_keys) <= n; 248, comment:# If you have less actual namespaces than number of NamespaceRanges; 249, comment:# to return, then just return the list of those namespaces.; 250, block; 251, assignment; 252, attribute; 253, argument_list; 254, list; 255, identifier:ns_range; 256, keyword_argument; 257, identifier:left; 258, identifier:right; 259, attribute; 260, argument_list; 261, assignment; 262, call; 263, identifier:ranges; 264, identifier:append; 265, identifier:left; 266, keyword_argument; 267, identifier:namespace_start; 268, identifier:MIN_NAMESPACE; 269, assignment; 270, identifier:len; 271, argument_list; 272, identifier:namespace_end; 273, identifier:MAX_NAMESPACE; 274, assignment; 275, identifier:NamespaceRange; 276, argument_list; 277, identifier:n; 278, integer:1; 279, call; 280, identifier:n; 281, expression_statement; 282, for_statement; 283, return_statement; 284, identifier:ranges; 285, list; 286, call; 287, identifier:normalized_start; 288, call; 289, identifier:_app; 290, identifier:_app; 291, identifier:namespace_range; 292, identifier:split_range; 293, identifier:right; 294, call; 295, attribute; 296, argument_list; 297, identifier:_app; 298, identifier:_app; 299, identifier:namespace_start; 300, attribute; 301, identifier:ns_ranges; 302, identifier:namespace_end; 303, call; 304, identifier:namespace_start; 305, identifier:namespace_end; 306, keyword_argument; 307, identifier:len; 308, argument_list; 309, assignment; 310, identifier:ns_key; 311, identifier:ns_keys; 312, block; 313, call; 314, call; 315, identifier:NamespaceRange; 316, argument_list; 317, identifier:NamespaceRange; 318, argument_list; 319, attribute; 320, argument_list; 321, identifier:ranges; 322, identifier:append; 323, identifier:right; 324, subscript; 325, identifier:namespace_start; 326, identifier:_ord_to_namespace; 327, argument_list; 328, identifier:_app; 329, identifier:_app; 330, identifier:ns_keys; 331, identifier:ns_range; 332, list; 333, expression_statement; 334, identifier:sorted; 335, argument_list; 336, identifier:NamespaceRange; 337, argument_list; 338, keyword_argument; 339, keyword_argument; 340, identifier:right; 341, identifier:normalized_start; 342, identifier:ns_ranges; 343, identifier:i; 344, binary_operator:_namespace_to_ord(ns_ranges[i+1].namespace_start) - 1; 345, call; 346, identifier:ns_range; 347, keyword_argument; 348, boolean_operator; 349, keyword_argument; 350, identifier:_app; 351, identifier:_app; 352, identifier:_app; 353, identifier:_app; 354, call; 355, integer:1; 356, attribute; 357, argument_list; 358, identifier:key; 359, lambda; 360, call; 361, string; 362, identifier:_app; 363, identifier:_app; 364, identifier:_namespace_to_ord; 365, argument_list; 366, identifier:ns_range; 367, identifier:append; 368, call; 369, lambda_parameters; 370, attribute; 371, attribute; 372, argument_list; 373, attribute; 374, identifier:NamespaceRange; 375, argument_list; 376, identifier:ns_range; 377, identifier:ns_range; 378, identifier:namespace_start; 379, subscript; 380, identifier:name; 381, subscript; 382, identifier:namespace_start; 383, boolean_operator; 384, boolean_operator; 385, keyword_argument; 386, identifier:ns_keys; 387, integer:0; 388, identifier:ns_ranges; 389, binary_operator:i+1; 390, call; 391, string; 392, call; 393, string; 394, identifier:_app; 395, identifier:_app; 396, identifier:i; 397, integer:1; 398, attribute; 399, argument_list; 400, attribute; 401, argument_list; 402, identifier:ns_key; 403, identifier:name; 404, identifier:ns_key; 405, identifier:name
code: def split(cls,
              n,
              contiguous,
              can_query=itertools.chain(itertools.repeat(True, 50),
                                        itertools.repeat(False)).next,
              _app=None):
      # pylint: disable=g-doc-args
      """Splits the complete NamespaceRange into n equally-sized NamespaceRanges.
  
      Args:
        n: The maximum number of NamespaceRanges to return. Fewer than n
            namespaces may be returned.
        contiguous: If True then the returned NamespaceRanges will cover the
            entire space of possible namespaces (i.e. from MIN_NAMESPACE to
            MAX_NAMESPACE) without gaps. If False then the returned
            NamespaceRanges may exclude namespaces that don't appear in the
            datastore.
        can_query: A function that returns True if split() can query the datastore
            to generate more fair namespace range splits, and False otherwise.
            If not set then split() is allowed to make 50 datastore queries.
  
      Returns:
        A list of at most n NamespaceRanges representing a near-equal distribution
        of actual existant datastore namespaces. The returned list will be sorted
        lexographically.
  
      Raises:
        ValueError: if n is < 1.
      """
      if n < 1:
        raise ValueError('n must be >= 1')
  
      ranges = None
      if can_query():
        if not contiguous:
          ns_keys = get_namespace_keys(_app, n + 1)
          if not ns_keys:
            return []
          else:
            if len(ns_keys) <= n:
              # If you have less actual namespaces than number of NamespaceRanges
              # to return, then just return the list of those namespaces.
              ns_range = []
              for ns_key in ns_keys:
                ns_range.append(NamespaceRange(ns_key.name() or '',
                                               ns_key.name() or '',
                                               _app=_app))
              return sorted(ns_range,
                            key=lambda ns_range: ns_range.namespace_start)
            # Use the first key and save the initial normalized_start() call.
            ranges = [NamespaceRange(ns_keys[0].name() or '', _app=_app)]
        else:
          ns_range = NamespaceRange(_app=_app).normalized_start()
          if ns_range is None:
            return [NamespaceRange(_app=_app)]
          ranges = [ns_range]
      else:
        ranges = [NamespaceRange(_app=_app)]
  
      singles = []
      while ranges and (len(ranges) + len(singles)) < n:
        namespace_range = ranges.pop(0)
        if namespace_range.is_single_namespace:
          singles.append(namespace_range)
        else:
          left, right = namespace_range.split_range()
          if can_query():
            right = right.normalized_start()
          if right is not None:
            ranges.append(right)
          ranges.append(left)
      ns_ranges = sorted(singles + ranges,
                         key=lambda ns_range: ns_range.namespace_start)
  
      if contiguous:
        if not ns_ranges:
          # This condition is possible if every namespace was deleted after the
          # first call to ns_range.normalized_start().
          return [NamespaceRange(_app=_app)]
  
        continuous_ns_ranges = []
        for i in range(len(ns_ranges)):
          if i == 0:
            namespace_start = MIN_NAMESPACE
          else:
            namespace_start = ns_ranges[i].namespace_start
  
          if i == len(ns_ranges) - 1:
            namespace_end = MAX_NAMESPACE
          else:
            namespace_end = _ord_to_namespace(
                _namespace_to_ord(ns_ranges[i+1].namespace_start) - 1)
  
          continuous_ns_ranges.append(NamespaceRange(namespace_start,
                                                     namespace_end,
                                                     _app=_app))
        return continuous_ns_ranges
      else:
        return ns_ranges