This repo contains code to mirror other repos. It also contains the code that is getting mirrored.
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

198 lines
4.8 KiB

  1. import sys
  2. from collections import deque
  3. Py36 = (sys.version_info[:2] >= (3, 6))
  4. class fzset(frozenset):
  5. def __repr__(self):
  6. return '{%s}' % ', '.join(map(repr, self))
  7. def classify_bool(seq, pred):
  8. true_elems = []
  9. false_elems = []
  10. for elem in seq:
  11. if pred(elem):
  12. true_elems.append(elem)
  13. else:
  14. false_elems.append(elem)
  15. return true_elems, false_elems
  16. def classify(seq, key=None, value=None):
  17. d = {}
  18. for item in seq:
  19. k = key(item) if (key is not None) else item
  20. v = value(item) if (value is not None) else item
  21. if k in d:
  22. d[k].append(v)
  23. else:
  24. d[k] = [v]
  25. return d
  26. def bfs(initial, expand):
  27. open_q = deque(list(initial))
  28. visited = set(open_q)
  29. while open_q:
  30. node = open_q.popleft()
  31. yield node
  32. for next_node in expand(node):
  33. if next_node not in visited:
  34. visited.add(next_node)
  35. open_q.append(next_node)
  36. def _serialize(value):
  37. if isinstance(value, Serialize):
  38. return value.serialize()
  39. elif isinstance(value, list):
  40. return [_serialize(elem) for elem in value]
  41. elif isinstance(value, frozenset):
  42. return list(value) # TODO reversible?
  43. elif isinstance(value, dict):
  44. return {key:_serialize(elem) for key, elem in value.items()}
  45. return value
  46. def _deserialize(data, namespace):
  47. if isinstance(data, dict):
  48. if '__type__' in data: # Object
  49. class_ = namespace[data['__type__']]
  50. return class_.deserialize(data)
  51. return {key:_deserialize(value, namespace) for key, value in data.items()}
  52. elif isinstance(data, list):
  53. return [_deserialize(value, namespace) for value in data]
  54. return data
  55. class Serialize(object):
  56. def serialize(self):
  57. fields = getattr(self, '__serialize_fields__')
  58. res = {f: _serialize(getattr(self, f)) for f in fields}
  59. res['__type__'] = type(self).__name__
  60. postprocess = getattr(self, '_serialize', None)
  61. if postprocess:
  62. postprocess(res)
  63. return res
  64. @classmethod
  65. def deserialize(cls, data):
  66. namespace = getattr(cls, '__serialize_namespace__', dict)
  67. namespace = {c.__name__:c for c in namespace()}
  68. fields = getattr(cls, '__serialize_fields__')
  69. inst = cls.__new__(cls)
  70. for f in fields:
  71. setattr(inst, f, _deserialize(data[f], namespace))
  72. postprocess = getattr(inst, '_deserialize', None)
  73. if postprocess:
  74. postprocess()
  75. return inst
  76. ###{standalone
  77. try:
  78. STRING_TYPE = basestring
  79. except NameError: # Python 3
  80. STRING_TYPE = str
  81. import types
  82. from functools import wraps, partial
  83. from contextlib import contextmanager
  84. Str = type(u'')
  85. try:
  86. classtype = types.ClassType # Python2
  87. except AttributeError:
  88. classtype = type # Python3
  89. def smart_decorator(f, create_decorator):
  90. if isinstance(f, types.FunctionType):
  91. return wraps(f)(create_decorator(f, True))
  92. elif isinstance(f, (classtype, type, types.BuiltinFunctionType)):
  93. return wraps(f)(create_decorator(f, False))
  94. elif isinstance(f, types.MethodType):
  95. return wraps(f)(create_decorator(f.__func__, True))
  96. elif isinstance(f, partial):
  97. # wraps does not work for partials in 2.7: https://bugs.python.org/issue3445
  98. return create_decorator(f.__func__, True)
  99. else:
  100. return create_decorator(f.__func__.__call__, True)
  101. def dedup_list(l):
  102. """Given a list (l) will removing duplicates from the list,
  103. preserving the original order of the list. Assumes that
  104. the list entrie are hashable."""
  105. dedup = set()
  106. return [ x for x in l if not (x in dedup or dedup.add(x))]
  107. ###}
  108. try:
  109. from contextlib import suppress # Python 3
  110. except ImportError:
  111. @contextmanager
  112. def suppress(*excs):
  113. '''Catch and dismiss the provided exception
  114. >>> x = 'hello'
  115. >>> with suppress(IndexError):
  116. ... x = x[10]
  117. >>> x
  118. 'hello'
  119. '''
  120. try:
  121. yield
  122. except excs:
  123. pass
  124. try:
  125. compare = cmp
  126. except NameError:
  127. def compare(a, b):
  128. if a == b:
  129. return 0
  130. elif a > b:
  131. return 1
  132. return -1
  133. import sre_parse
  134. import sre_constants
  135. def get_regexp_width(regexp):
  136. try:
  137. return sre_parse.parse(regexp).getwidth()
  138. except sre_constants.error:
  139. raise ValueError(regexp)
  140. class Enumerator:
  141. def __init__(self):
  142. self.enums = {}
  143. def get(self, item):
  144. if item not in self.enums:
  145. self.enums[item] = len(self.enums)
  146. return self.enums[item]
  147. def __len__(self):
  148. return len(self.enums)
  149. def reversed(self):
  150. r = {v: k for k, v in self.enums.items()}
  151. assert len(r) == len(self.enums)
  152. return r