| 21 | virtual ~MatrixBandPartGradTest() = default; |
| 22 | |
| 23 | virtual bool run(int precision) { |
| 24 | std::vector<int> shape = {3, 2, 3, 2}; |
| 25 | const int len = shape[0] * shape[1] * shape[2] * shape[3]; |
| 26 | auto input = _Input(shape, NCHW); |
| 27 | const float inpudata[] = { -0.94003415f, -0.03546342f, -0.01028545f, 1.2092209f , 1.5427123f , |
| 28 | 1.0838836f , 0.5939991f , 2.017224f , 0.2702435f , 1.1762271f , |
| 29 | -0.95548075f, -0.12556452f, -1.4086435f , -0.13807571f, -0.23514274f, |
| 30 | -0.5025484f , 0.93871444f, -0.5169497f , -1.5226837f , -0.8545326f , |
| 31 | 0.340934f , 0.25505793f, 1.7961069f , -0.7955173f , -0.16109313f, |
| 32 | 1.3417882f , 0.9252207f , -0.69964254f, -0.5392309f , 0.4769467f , |
| 33 | -0.33865267f, -0.5568984f , -0.53030866f, -0.07422069f, -0.7438325f , |
| 34 | -0.06075661f}; |
| 35 | auto inputPtr = input->writeMap<float>(); |
| 36 | memcpy(inputPtr, inpudata, len * sizeof(float)); |
| 37 | |
| 38 | auto lower = _Scalar<int>(0); |
| 39 | auto upper = _Scalar<int>(1); |
| 40 | auto output = _MatrixBandPart(input, lower, upper); |
| 41 | |
| 42 | auto opExpr = output->expr().first; |
| 43 | auto grad = OpGrad::get(opExpr->get()->type()); |
| 44 | const float outputDiff[] = { 0.92951214f, -1.3656238f , 0.9058341f , 0.21897921f, -0.5062561f , |
| 45 | 0.29703847f, -0.5324379f , 0.8826049f , -0.9250548f , 1.8164085f , |
| 46 | -1.7761891f , 1.2291343f , 0.45859334f, 0.09624046f, -0.8051032f , |
| 47 | 0.446291f , 0.9178219f , -0.7392022f , 2.31639f , -0.8006644f , |
| 48 | 0.5834905f , 1.5046587f , -0.11566874f, -2.449344f , -1.2720072f , |
| 49 | -0.55631214f, -0.12848197f, -1.2433224f , -0.46224716f, 0.57611173f, |
| 50 | -1.0455252f , 1.1562699f , -1.2612194f , 0.46669045f, 0.38025302f, |
| 51 | -0.70845205f}; |
| 52 | auto inputGrad = grad->onGrad(opExpr, {_Const(outputDiff, shape)}); |
| 53 | |
| 54 | const std::vector<float> expectedOutput = { 0.92951214f, -1.3656238f , 0.f , 0.21897921f, -0.f , |
| 55 | 0.f , -0.5324379f , 0.8826049f , -0.f , 1.8164085f , |
| 56 | -0.f , 0.f , 0.45859334f, 0.09624046f, -0.f , |
| 57 | 0.446291f , 0.f , -0.f , 2.31639f , -0.8006644f , |
| 58 | 0.f , 1.5046587f , -0.f , -0.f , -1.2720072f , |
| 59 | -0.55631214f, -0.f , -1.2433224f , -0.f , 0.f , |
| 60 | -1.0455252f , 1.1562699f , -0.f , 0.46669045f, 0.f , |
| 61 | -0.f}; |
| 62 | auto gotOutput = inputGrad[0]->readMap<float>(); |
| 63 | |
| 64 | for (int i = 0; i < len; ++i) { |
| 65 | auto diff = ::fabsf(gotOutput[i] - expectedOutput[i]); |
| 66 | if (diff > 0.0001) { |
| 67 | MNN_ERROR("%s grad test failed, expected: %f, but got: %f!\n", name, expectedOutput[i], gotOutput[i]); |
| 68 | return false; |
| 69 | } |
| 70 | } |
| 71 | |
| 72 | return true; |
| 73 | } |
| 74 | }; |
| 75 | |
| 76 | MNNTestSuiteRegister(MatrixBandPartGradTest, "grad/matrix_band_part"); |