docs: public static int solveColB(DMatrixSparseCSC G, boolean lower,
                                  DMatrixSparseCSC B, int colB, double x[],
                                  @Nullable int pinv[], @Nullable IGrowArray g_xi, int []w) {
  
          // NOTE x's length is the number of rows in G and not cols. This might be more than needed if a tall matrix,
          // but a change to remove it would require more thought
          int X_rows = G.numCols;
          int[] xi = UtilEjml.adjust(g_xi,X_rows);
          int top = searchNzRowsInX(G, B, colB, pinv, xi, w);
  
          // sparse clear of x.
          for( int p = top; p < X_rows; p++ )
              x[xi[p]] = 0;
  
          // copy B into X
          int idxB0 = B.col_idx[colB];
          int idxB1 = B.col_idx[colB+1];
          for( int p = idxB0; p < idxB1; p++ ) {
              x[B.nz_rows[p]] = B.nz_values[p];
          }
  
          for (int px = top; px < X_rows; px++) {
              int j = xi[px];
              int J = pinv != null ? pinv[j] : j;
              if( J < 0 )
                  continue;
              int p,q;
              if( lower ) {
                  x[j] /= G.nz_values[G.col_idx[J]];
                  p = G.col_idx[J]+1;
                  q = G.col_idx[J+1];
              } else {
                  x[j] /= G.nz_values[G.col_idx[J+1]-1];
                  p = G.col_idx[J];
                  q = G.col_idx[J+1]-1;
              }
              for(;p<q;p++) {
                  // NOTE: This will manipulate elements in x which are already known to have a zero value
                  // I guess this is faster/easier than actively trying to avoid those elements. I don't see an obvious
                  // way to improve it
                  x[G.nz_rows[p]] -= G.nz_values[p]*x[j];
              }
          }
  
          return top;
      }