text: from __future__ import print_function
  from __future__ import absolute_import
  from __future__ import division
  
  from compas.utilities import pairwise
  from compas.utilities import geometric_key
  
  __all__ = [
      'network_join_edges',
      'network_polylines'
  ]
  
  
  def network_join_edges(network, key):
      """Join the edges incidental on the given node, if there are exactly two incident edges.
  
      Parameters
      ----------
      network : :class:`~compas.geometry.Network`
          A network data structure.
      key : hashable
          The node identifier.
  
      Returns
      -------
      None
          The network is modified in place.
  
      Notes
      -----
      A new edge is created to replace the two joined edges.
      The attributes of the joined edges are not transferred to the new edge.
      Therefore, the new edge has only default edge attributes.
  
      """
      nbrs = network.vertex_neighbors(key)
      if len(nbrs) != 2:
          return
      a, b = nbrs
      if a in network.edge[key]:
          del network.edge[key][a]
      else:
          del network.edge[a][key]
      del network.halfedge[key][a]
      del network.halfedge[a][key]
      if b in network.edge[key]:
          del network.edge[key][b]
      else:
          del network.edge[b][key]
      del network.halfedge[key][b]
      del network.halfedge[b][key]
      del network.vertex[key]
      del network.halfedge[key]
      del network.edge[key]
      # set attributes based on average of two joining edges?
      network.add_edge(a, b)
  
  
  def network_polylines(network, splits=None):
      """Join network edges into polylines.
  
      The polylines stop at points with a valency different from 2 in the network of line.
      Optional splits can be included.
  
      Parameters
      ----------
      network : Network
          A network.
      splits : sequence[[float, float, float] | :class:`~compas.geometry.Point`], optional
          List of point coordinates for polyline splits.
  
      Returns
      -------
      list[list[[float, float, float]]]
          The joined polylines.
          If a polyline is closed, the two extremities are the same.
  
      Examples
      --------
      Joining the lines (a, b), (b, c), (c, d), (c, e) and (e, f),
      where a ... f are different point coordinates.
      This will result in the following polylines (a, b, c), (c, d) and (c, e, f).
  
      >>> from compas.datastructures import Network
      >>> a = [0., 0., 0.]
      >>> b = [1., 0., 0.]
      >>> c = [2., 0., 0.]
      >>> d = [2., 1., 0.]
      >>> e = [3., 0., 0.]
      >>> f = [4., 0., 0.]
      >>> lines = [(a, b), (b, c), (c, d), (c, e), (e, f)]
      >>> network = Network.from_lines(lines)
      >>> len(network_polylines(network)) == 3
      True
  
      """
      # geometric keys of split points
      if splits is None:
          splits = []
      stop_geom_keys = set([geometric_key(xyz) for xyz in splits])
  
      polylines = []
      edges_to_visit = set(network.edges())
  
      # initiate a polyline from an unvisited edge
      while len(edges_to_visit) > 0:
          polyline = list(edges_to_visit.pop())
  
          # get adjacent edges until the polyline is closed...
          while polyline[0] != polyline[-1]:
  
              # ... or until both end are non-two-valent vertices
              if len(network.neighbors(polyline[-1])) != 2 or geometric_key(network.node_coordinates(polyline[-1])) in stop_geom_keys:
                  polyline = list(reversed(polyline))
                  if len(network.neighbors(polyline[-1])) != 2 or geometric_key(network.node_coordinates(polyline[-1])) in stop_geom_keys:
                      break
  
              # add next edge
              polyline.append([nbr for nbr in network.neighbors(polyline[-1]) if nbr != polyline[-2]][0])
  
          # delete polyline edges from the list of univisted edges
          for u, v in pairwise(polyline):
              if (u, v) in edges_to_visit:
                  edges_to_visit.remove((u, v))
              elif (v, u) in edges_to_visit:
                  edges_to_visit.remove((v, u))
  
          polylines.append(polyline)
  
      return [[network.node_coordinates(vkey) for vkey in polyline] for polyline in polylines]
  