code: def perpendicular_directions(v, num=30, half=False):
      r"""Computes n evenly spaced perpendicular directions relative to a given
      vector v
  
      Parameters
      ----------
      v : array (3,)
          Array containing the three cartesian coordinates of vector v
      num : int, optional
          Number of perpendicular directions to generate
      half : bool, optional
          If half is True, perpendicular directions are sampled on half of the
          unit circumference perpendicular to v, otherwive perpendicular
          directions are sampled on the full circumference. Default of half is
          False
  
      Returns
      -------
      psamples : array (n, 3)
          array of vectors perpendicular to v
  
      Notes
      -----
      Perpendicular directions are estimated using the following two step
      procedure:
  
          1) the perpendicular directions are first sampled in a unit
          circumference parallel to the plane normal to the x-axis.
  
          2) Samples are then rotated and aligned to the plane normal to vector
          v. The rotational matrix for this rotation is constructed as reference
          frame basis which axis are the following:
              - The first axis is vector v
              - The second axis is defined as the normalized vector given by the
              cross product between vector v and the unit vector aligned to the
              x-axis
              - The third axis is defined as the cross product between the
              previous computed vector and vector v.
  
      Following this two steps, coordinates of the final perpendicular directions
      are given as:
  
      .. math::
  
          \left [ -\sin(a_{i}) \sqrt{{v_{y}}^{2}+{v_{z}}^{2}}
          \; , \;
          \frac{v_{x}v_{y}\sin(a_{i})-v_{z}\cos(a_{i})}
          {\sqrt{{v_{y}}^{2}+{v_{z}}^{2}}}
          \; , \;
          \frac{v_{x}v_{z}\sin(a_{i})-v_{y}\cos(a_{i})}
          {\sqrt{{v_{y}}^{2}+{v_{z}}^{2}}} \right  ]
  
      This procedure has a singularity when vector v is aligned to the x-axis. To
      solve this singularity, perpendicular directions in procedure's step 1 are
      defined in the plane normal to y-axis and the second axis of the rotated
      frame of reference is computed as the normalized vector given by the cross
      product between vector v and the unit vector aligned to the y-axis.
      Following this, the coordinates of the perpendicular directions are given
      as:
  
          \left [ -\frac{\left (v_{x}v_{y}\sin(a_{i})+v_{z}\cos(a_{i}) \right )}
          {\sqrt{{v_{x}}^{2}+{v_{z}}^{2}}}
          \; , \;
          \sin(a_{i}) \sqrt{{v_{x}}^{2}+{v_{z}}^{2}}
          \; , \;
          \frac{v_{y}v_{z}\sin(a_{i})+v_{x}\cos(a_{i})}
          {\sqrt{{v_{x}}^{2}+{v_{z}}^{2}}} \right  ]
  
      For more details on this calculation, see
      `here <https://gsoc2015dipydki.blogspot.com/2015/07/rnh-post-8-computing-perpendicular.html>`_.
  
      """  # noqa: E501
      v = np.array(v, dtype=float)
  
      # Float error used for floats comparison
      er = np.finfo(v[0]).eps * 1e3
  
      # Define circumference or semi-circumference
      if half is True:
          a = np.linspace(0.0, math.pi, num=num, endpoint=False)
      else:
          a = np.linspace(0.0, 2 * math.pi, num=num, endpoint=False)
  
      cosa = np.cos(a)
      sina = np.sin(a)
  
      # Check if vector is not aligned to the x axis
      if abs(v[0] - 1.0) > er:
          sq = np.sqrt(v[1] ** 2 + v[2] ** 2)
          psamples = np.array(
              [
                  -sq * sina,
                  (v[0] * v[1] * sina - v[2] * cosa) / sq,
                  (v[0] * v[2] * sina + v[1] * cosa) / sq,
              ]
          )
      else:
          sq = np.sqrt(v[0] ** 2 + v[2] ** 2)
          psamples = np.array(
              [
                  -(v[2] * cosa + v[0] * v[1] * sina) / sq,
                  sina * sq,
                  (v[0] * cosa - v[2] * v[1] * sina) / sq,
              ]
          )
  
      return psamples.T
  
imports: import itertools
  import math
  import numpy
  import numpy.linalg
label_desc: Use image node_id 19 for calling a global function with example usage: perpendicular_directions(v, num, half) and returns: psamples