code: def read_graph(filename, directed=False, weighted=False, default_weight=None):
      
      with open(filename, 'r') as f:
          while True:
              line = f.readline()         # ignore leading comments
              if line[0] != '#':
                  break
          nb_nodes, nb_edges = tuple(map(int, line.split()))
          graph = [[] for u in range(nb_nodes)]
          if weighted:
              weight = [[default_weight] * nb_nodes for v in range(nb_nodes)]
              for v in range(nb_nodes):
                  weight[v][v] = 0
              for _ in range(nb_edges):
                  u, v, w = readtab(f, int)
                  graph[u].append(v)
                  weight[u][v] = w
                  if not directed:
                      graph[v].append(u)
                      weight[v][u] = w
              return graph, weight
          else:
              for _ in range(nb_edges):
                  # si le fichier contient des poids, ils seront ignorés
                  u, v = readtab(f, int)[:2]
                  graph[u].append(v)
                  if not directed:
                      graph[v].append(u)
              return graph
docs: Read a graph from a text file
  
      :param filename: plain text file. All numbers are separated by space.
                Starts with a line containing n (#vertices) and m (#edges).
                Then m lines follow, for each edge.
                Vertices are numbered from 0 to n-1.
                Line for unweighted edge u,v contains two integers u, v.
                Line for weighted edge u,v contains three integers u, v, w[u,v].
  
      :param directed: true for a directed graph, false for undirected
      :param weighted: true for an edge weighted graph
      :returns: graph in listlist format, possibly followed by weight matrix
      :complexity: O(n + m) for unweighted graph,
                   :math:`O(n^2)` for weighted graph