docs: def fisher(yhat,y,samples=False):
      """Fisher criterion"""
      classes = np.unique(y)
      mu = np.zeros(len(classes))
      v = np.zeros(len(classes))
      # pdb.set_trace()
      for c in classes.astype(int):
          mu[c] = np.mean(yhat[y==c])
          v[c] = np.var(yhat[y==c])
  
      if not samples:
          fisher = 0
          for c1,c2 in pairwise(classes.astype(int)):
              fisher += np.abs(mu[c1] - mu[c2])/np.sqrt(v[c1]+v[c2])
      else:
          # lexicase version
          fisher = np.zeros(len(yhat))
          # get closests classes to each class (min mu distance)
          mu_d = pairwise_distances(mu.reshape(-1,1))
          min_mu=np.zeros(len(classes),dtype=int)
          for i in np.arange(len(min_mu)):
              min_mu[i] = np.argsort(mu_d[i])[1]
          # for c1, pairwise(classes.astype(int)):
          #     min_mu[c1] = np.argmin()
          for i,l in enumerate(yhat.astype(int)):
              fisher[i] = np.abs(l - mu[min_mu[y[i]]])/np.sqrt(v[y[i]]+v[min_mu[y[i]]])
  
      # pdb.set_trace()
      return fisher