def cycles(self):
        def walk_node(node, seen):
            if node in seen:
                yield (node,)
                return
            seen.add(node)
            for edge in self.edges[node]:
                for cycle in walk_node(edge, set(seen)):
                    yield (node,) + cycle
        cycles = chain.from_iterable(
            (walk_node(node, set()) for node in self.nodes))
        shortest = set()
        for cycle in sorted(cycles, key=len):
            for el in shortest:
                if set(el).issubset(set(cycle)):
                    break
            else:
                shortest.add(cycle)
        return shortest