@Override
  public double residual(final Object b) {
    double sum = 0;
    if (b instanceof AbstractDataset) {
      final AbstractDataset bds = (AbstractDataset) b;
      checkCompatibility(bds);

      final IndexIterator it1 = getIterator();
      final IndexIterator it2 = bds.getIterator();
      final int bis = bds.getElementsPerItem();

      if (bis == 1) {
        double comp = 0;
        while (it1.hasNext() && it2.hasNext()) {
          final double db = bds.getElementDoubleAbs(it2.index);
          for (int i = 0; i < isize; i++) {
            final double diff = data[it1.index + i] - db;
            final double err = diff * diff - comp;
            final double temp = sum + err;
            comp = (temp - sum) - err;
            sum = temp;
          }
        }
      } else if (bis == isize) {
        double comp = 0;
        while (it1.hasNext() && it2.hasNext()) {
          for (int i = 0; i < isize; i++) {
            final double diff = data[it1.index + i] - bds.getElementDoubleAbs(it2.index + i);
            final double err = diff * diff - comp;
            final double temp = sum + err;
            comp = (temp - sum) - err;
            sum = temp;
          }
        }
      } else {
        throw new IllegalArgumentException(
            "Argument does not have same number of elements per item or is not a non-compound dataset");
      }
    } else {
      final double[] vr = toDoubleArray(b, isize);
      final IndexIterator it1 = getIterator();

      double comp = 0;
      while (it1.hasNext()) {
        for (int i = 0; i < isize; i++) {
          final double diff = data[it1.index + i] - vr[i];
          final double err = diff * diff - comp;
          final double temp = sum + err;
          comp = (temp - sum) - err;
          sum = temp;
        }
      }
    }
    return sum;
  }
  @Override
  public CompoundIntegerDataset ipower(final Object b) {
    if (b instanceof AbstractDataset) {
      final AbstractDataset bds = (AbstractDataset) b;
      checkCompatibility(bds);

      final IndexIterator it1 = getIterator();
      final IndexIterator it2 = bds.getIterator();
      final int bis = bds.getElementsPerItem();

      if (bis == 1) {
        while (it1.hasNext() && it2.hasNext()) {
          final int db =
              (int) bds.getElementLongAbs(it2.index); // PRIM_TYPE // GET_ELEMENT_WITH_CAST
          for (int i = 0; i < isize; i++) {
            final double v = Math.pow(data[it1.index + i], db);
            if (Double.isInfinite(v) || Double.isNaN(v)) { // INT_ZEROTEST
              data[it1.index + i] = 0; // INT_ZEROTEST // CLASS_TYPE
            } else { // INT_ZEROTEST
              data[it1.index + i] = (int) (long) v; // PRIM_TYPE_LONG // ADD_CAST
            } // INT_ZEROTEST
          }
        }
      } else if (bis == isize) {
        while (it1.hasNext() && it2.hasNext()) {
          for (int i = 0; i < isize; i++) {
            final double v = Math.pow(data[it1.index + i], bds.getElementDoubleAbs(it2.index + i));
            if (Double.isInfinite(v) || Double.isNaN(v)) { // INT_ZEROTEST
              data[it1.index + i] = 0; // INT_ZEROTEST // CLASS_TYPE
            } else { // INT_ZEROTEST
              data[it1.index + i] = (int) (long) v; // PRIM_TYPE_LONG // ADD_CAST
            } // INT_ZEROTEST
          }
        }
      } else {
        throw new IllegalArgumentException(
            "Argument does not have same number of elements per item or is not a non-compound dataset");
      }
    } else {
      final int[] vr = toIntegerArray(b, isize); // PRIM_TYPE // CLASS_TYPE
      final IndexIterator it1 = getIterator();

      while (it1.hasNext()) {
        for (int i = 0; i < isize; i++) {
          final double v = Math.pow(data[it1.index + i], vr[i]);
          if (Double.isInfinite(v) || Double.isNaN(v)) { // INT_ZEROTEST
            data[it1.index + i] = 0; // INT_ZEROTEST // CLASS_TYPE
          } else { // INT_ZEROTEST
            data[it1.index + i] = (int) (long) v; // PRIM_TYPE_LONG // ADD_CAST
          } // INT_ZEROTEST
        }
      }
    }
    setDirty();
    return this;
  }