| 42 | |
| 43 | template <typename Dtype> |
| 44 | void PowerLayer<Dtype>::Backward_cpu(const vector<Blob<Dtype>*>& top, |
| 45 | const vector<bool>& propagate_down, |
| 46 | const vector<Blob<Dtype>*>& bottom) { |
| 47 | if (propagate_down[0]) { |
| 48 | Dtype* bottom_diff = bottom[0]->mutable_cpu_diff(); |
| 49 | const int count = bottom[0]->count(); |
| 50 | const Dtype* top_diff = top[0]->cpu_diff(); |
| 51 | if (diff_scale_ == Dtype(0) || power_ == Dtype(1)) { |
| 52 | caffe_set(count, diff_scale_, bottom_diff); |
| 53 | } else { |
| 54 | const Dtype* bottom_data = bottom[0]->cpu_data(); |
| 55 | // Compute dy/dx = scale * power * (shift + scale * x)^(power - 1) |
| 56 | // = diff_scale * y / (shift + scale * x) |
| 57 | if (power_ == Dtype(2)) { |
| 58 | // Special case for y = (shift + scale * x)^2 |
| 59 | // -> dy/dx = 2 * scale * (shift + scale * x) |
| 60 | // = diff_scale * shift + diff_scale * scale * x |
| 61 | caffe_cpu_axpby(count, diff_scale_ * scale_, bottom_data, |
| 62 | Dtype(0), bottom_diff); |
| 63 | if (shift_ != Dtype(0)) { |
| 64 | caffe_add_scalar(count, diff_scale_ * shift_, bottom_diff); |
| 65 | } |
| 66 | } else if (shift_ == Dtype(0)) { |
| 67 | // Special case for y = (scale * x)^power |
| 68 | // -> dy/dx = scale * power * (scale * x)^(power - 1) |
| 69 | // = scale * power * (scale * x)^power * (scale * x)^(-1) |
| 70 | // = power * y / x |
| 71 | const Dtype* top_data = top[0]->cpu_data(); |
| 72 | caffe_div(count, top_data, bottom_data, bottom_diff); |
| 73 | caffe_scal(count, power_, bottom_diff); |
| 74 | } else { |
| 75 | caffe_copy(count, bottom_data, bottom_diff); |
| 76 | if (scale_ != Dtype(1)) { |
| 77 | caffe_scal(count, scale_, bottom_diff); |
| 78 | } |
| 79 | if (shift_ != Dtype(0)) { |
| 80 | caffe_add_scalar(count, shift_, bottom_diff); |
| 81 | } |
| 82 | const Dtype* top_data = top[0]->cpu_data(); |
| 83 | caffe_div<Dtype>(count, top_data, bottom_diff, bottom_diff); |
| 84 | if (diff_scale_ != Dtype(1)) { |
| 85 | caffe_scal(count, diff_scale_, bottom_diff); |
| 86 | } |
| 87 | } |
| 88 | } |
| 89 | if (diff_scale_ != Dtype(0)) { |
| 90 | caffe_mul(count, top_diff, bottom_diff, bottom_diff); |
| 91 | } |
| 92 | } |
| 93 | } |
| 94 | |
| 95 | #ifdef CPU_ONLY |
| 96 | STUB_GPU(PowerLayer); |
nothing calls this directly
no test coverage detected