Beispiel #1
0
        public void EmbedIDRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int inputCount  = Mother.Dice.Next(2, 30);
            int outputCount = Mother.Dice.Next(1, 30);
            int batchCount  = Mother.Dice.Next(1, 5);

            int[,] input = (int[, ])Enumerable.Repeat(0, batchCount * inputCount).ToNdArray(batchCount, inputCount);
            input[0, 0]  = 1;

            Real[,,] dummyGy = Initializer.GetRandomValues <Real[, , ]>(batchCount, inputCount, outputCount);
            Real[,] w        = Initializer.GetRandomValues <Real[, ]>(inputCount, outputCount);

            //Chainer
            NChainer.EmbedID <Real> cEmbedId = new NChainer.EmbedID <Real>(inputCount, outputCount, w);

            Variable <int> cX = new Variable <int>(input);

            Variable <Real> cY = cEmbedId.Forward(cX);

            cY.Grad = dummyGy;

            cY.Backward();


            //KelpNet
            EmbedID <Real> embedId = new EmbedID <Real>(inputCount, outputCount, w);

            NdArray <Real> x = new NdArray <Real>(input, asBatch: true);

            NdArray <Real> y = embedId.Forward(x)[0];

            y.Grad = dummyGy.Flatten();

            y.Backward();


            Real[] cYdata = ((Real[, , ])cY.Data).Flatten();

            Real[] cWgrad = ((Real[, ])cEmbedId.W.Grad).Flatten();

            //許容範囲を算出
            Real delta = 0.00001f;

            //y
            Assert.AreEqual(cYdata.Length, y.Data.Length);
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //W.grad
            Assert.AreEqual(cWgrad.Length, embedId.Weight.Grad.Length);
            for (int i = 0; i < embedId.Weight.Grad.Length; i++)
            {
                Assert.AreEqual(cWgrad[i], embedId.Weight.Grad[i], delta);
            }
        }
        public void EmbedIDRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int inputCount  = Mother.Dice.Next(2, 30);
            int outputCount = Mother.Dice.Next(1, 30);
            int batchCount  = Mother.Dice.Next(1, 5);

            int[,] input = (int[, ])Enumerable.Repeat(0, batchCount * inputCount).ToNdArray(batchCount, inputCount);
            input[0, 0]  = 1;

            Real[,,] dummyGy = (Real[, , ])Initializer.GetRealNdArray(new[] { batchCount, inputCount, outputCount });
            Real[,] w        = (Real[, ])Initializer.GetRealNdArray(new[] { inputCount, outputCount });

            //Chainer
            NChainer.EmbedID <Real> cEmbedId = new NChainer.EmbedID <Real>(inputCount, outputCount, Real.ToBaseNdArray(w));

            Variable <int> cX = new Variable <int>(input);

            Variable <Real> cY = cEmbedId.Forward(cX);

            cY.Grad = Real.ToBaseNdArray(dummyGy);

            cY.Backward();


            //KelpNet
            KelpNet.EmbedID embedId = new KelpNet.EmbedID(inputCount, outputCount, w);

            NdArray x = new NdArray(Real.ToRealArray(input), new[] { inputCount }, batchCount);

            NdArray y = embedId.Forward(x)[0];

            y.Grad = Real.ToRealArray(dummyGy);

            y.Backward();


            Real[] cYdata = Real.ToRealArray((Real[, , ])cY.Data);

            Real[] cWgrad = Real.ToRealArray((Real[, ])cEmbedId.W.Grad);

            //許容範囲を算出
            double delta = 0.00001;

            //y
            Assert.AreEqual(cYdata.Length, y.Data.Length);
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //W.grad
            Assert.AreEqual(cWgrad.Length, embedId.Weight.Grad.Length);
            for (int i = 0; i < embedId.Weight.Grad.Length; i++)
            {
                Assert.AreEqual(cWgrad[i], embedId.Weight.Grad[i], delta);
            }
        }
Beispiel #3
0
        public void AdamRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int inputCount = Mother.Dice.Next(2, 50);
            int outputCount = Mother.Dice.Next(2, 50);
            int batchCount = Mother.Dice.Next(1, 5);

            Real[,] input = (Real[,])Initializer.GetRealNdArray(new[] { batchCount, inputCount });
            Real[,] dummyGy = (Real[,])Initializer.GetRealNdArray(new[] { batchCount, outputCount });
            Real[,] w = (Real[,])Initializer.GetRealNdArray(new[] { outputCount, inputCount });
            Real[] b = Initializer.GetRealArray(outputCount);


            float alpha = (float)Mother.Dice.NextDouble(); //0.001f
            float beta1 = (float)Mother.Dice.NextDouble(); //0.9f;
            float beta2 = (float)Mother.Dice.NextDouble(); //0.999f;
            float eps = (float)Mother.Dice.NextDouble(); //1e-08f;
            float eta = (float)Mother.Dice.NextDouble(); //1.0f;

            //Chainer
            NChainer.Linear<Real> cLinear = new NChainer.Linear<Real>(inputCount, outputCount, false, Real.ToBaseNdArray(w), Real.ToBaseArray(b));
            NChainer.Adam<Real> cAdam = new NChainer.Adam<Real>(alpha, beta1, beta2, eps, eta);
            cAdam.Setup(cLinear);

            Variable<Real> cX = new Variable<Real>(Real.ToBaseNdArray(input));

            Variable<Real> cY = cLinear.Forward(cX);
            cY.Grad = Real.ToBaseNdArray(dummyGy);

            cY.Backward();

            cAdam.Update();

            //KelpNet
            KelpNet.CL.Linear linear = new KelpNet.CL.Linear(inputCount, outputCount, false, w, b);
            KelpNet.Adam adam = new Adam(alpha, beta1, beta2, eps, eta);
            adam.SetUp(linear);

            NdArray x = new NdArray(Real.ToRealArray(input), new[] { inputCount }, batchCount);

            NdArray y = linear.Forward(x)[0];
            y.Grad = Real.ToRealArray(dummyGy);

            y.Backward();

            adam.Update();


            Real[] cW = Real.ToRealArray((Real[,])cLinear.W.Data);
            Real[] cb = (Real[])cLinear.b.Data;

            //許容範囲を算出
            double delta = 0.00001;

            //W.grad
            Assert.AreEqual(cW.Length, linear.Weight.Data.Length);
            for (int i = 0; i < linear.Weight.Data.Length; i++)
            {
                Assert.AreEqual(cW[i], linear.Weight.Data[i], delta);
            }

            //b.grad
            Assert.AreEqual(cb.Length, linear.Bias.Data.Length);
            for (int i = 0; i < linear.Bias.Data.Length; i++)
            {
                Assert.AreEqual(cb[i], linear.Bias.Data[i], delta);
            }
        }
Beispiel #4
0
        public void RandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int inputCount  = 1 + Mother.Dice.Next() % 49;
            int outputCount = 1 + Mother.Dice.Next() % 49;

            Real[,] input = (Real[, ])Initializer.GetRealNdArray(new[] { 1, inputCount });

            Real[,] dummyGy = (Real[, ])Initializer.GetRealNdArray(new[] { 1, outputCount });
            Real[,] w       = (Real[, ])Initializer.GetRealNdArray(new[] { outputCount, inputCount });

            Real[] b = Initializer.GetRealArray(outputCount);

            //Chainer
            NChainer.Linear <Real> cLinear = new NChainer.Linear <Real>(inputCount, outputCount, false, Real.ToBaseNdArray(w), Real.ToBaseArray(b));

            Variable <Real> cX = new Variable <Real>(Real.ToBaseNdArray(input));

            Variable <Real> cY = cLinear.Forward(cX);

            cY.Grad = Real.ToBaseNdArray(dummyGy);

            cY.Backward();


            //KelpNet
            KelpNet.Linear linear = new KelpNet.Linear(inputCount, outputCount, false, w, b);

            NdArray x = new NdArray(input);

            NdArray y = linear.Forward(x)[0];

            y.Grad = Real.ToRealArray(dummyGy);

            y.Backward();


            Real[] cYdata = Real.ToRealArray((Real[, ])cY.Data);
            Real[] cXgrad = Real.ToRealArray((Real[, ])cX.Grad);

            Real[] cWgrad = Real.ToRealArray((Real[, ])cLinear.W.Grad);
            Real[] cbgrad = (Real[])cLinear.b.Grad;

            //許容範囲を算出
            double delta = 0.00001;

            //y
            Assert.AreEqual(cYdata.Length, y.Data.Length);
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //x.grad
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);
            for (int i = 0; i < x.Grad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }

            //W.grad
            Assert.AreEqual(cWgrad.Length, linear.Weight.Grad.Length);
            for (int i = 0; i < linear.Weight.Grad.Length; i++)
            {
                Assert.AreEqual(cWgrad[i], linear.Weight.Grad[i], delta);
            }

            //b.grad
            Assert.AreEqual(cbgrad.Length, linear.Bias.Grad.Length);
            for (int i = 0; i < linear.Bias.Grad.Length; i++)
            {
                Assert.AreEqual(cbgrad[i], linear.Bias.Grad[i], delta);
            }
        }
Beispiel #5
0
 //Backward
 public override void Backward(params NdArray[] ys)
 {
     NdArray.Backward(ys[0]);
 }
        public void RandomTest(bool gpuEnable)
        {
            Python.Initialize();
            Chainer.Initialize();

            int batchCount = Mother.Dice.Next(1, 5);
            int inChCount  = Mother.Dice.Next(1, 5);
            int outChCount = Mother.Dice.Next(1, 5);
            int wideSize   = Mother.Dice.Next(8, 32);
            int heightSize = Mother.Dice.Next(8, 32);

            int kWidth  = Mother.Dice.Next(1, 5);
            int kHeight = Mother.Dice.Next(1, 5);

            int strideX = Mother.Dice.Next(1, 5);
            int strideY = Mother.Dice.Next(1, 5);

            int padX = Mother.Dice.Next(0, 5);
            int padY = Mother.Dice.Next(0, 5);

            int outputHeight = (int)Math.Floor((heightSize - kHeight + padY * 2.0) / strideY) + 1;
            int outputWidth  = (int)Math.Floor((wideSize - kWidth + padX * 2.0) / strideX) + 1;

            Real[,,,] input = (Real[, , , ])Initializer.GetRealNdArray(new[] { batchCount, inChCount, heightSize, wideSize });

            Real[,,,] dummyGy = (Real[, , , ])Initializer.GetRealNdArray(new[] { batchCount, outChCount, outputHeight, outputWidth });
            Real[,,,] w       = (Real[, , , ])Initializer.GetRealNdArray(new[] { outChCount, inChCount, kHeight, kWidth });

            Real[] b = Initializer.GetRealArray(outChCount);

            //Chainer
            NChainer.Convolution2D <Real> cConvolotion2D = new NChainer.Convolution2D <Real>(
                inChCount, outChCount,
                new[] { kHeight, kWidth },
                new[] { strideY, strideX },
                new[] { padY, padX },
                false,
                Real.ToBaseNdArray(w),
                Real.ToBaseArray(b));

            Variable <Real> cX = new Variable <Real>(Real.ToBaseNdArray(input));

            Variable <Real> cY = cConvolotion2D.Forward(cX);

            cY.Grad = Real.ToBaseNdArray(dummyGy);

            cY.Backward();


            //KelpNet
            KelpNet.CL.Convolution2D convolution2D = new KelpNet.CL.Convolution2D(
                inChCount, outChCount,
                new[] { kWidth, kHeight },
                new[] { strideX, strideY },
                new[] { padX, padY },
                false, w, b, gpuEnable: gpuEnable);

            NdArray x = new NdArray(Real.ToRealArray(input), new[] { inChCount, heightSize, wideSize }, batchCount);

            NdArray y = convolution2D.Forward(x)[0];

            y.Grad = Real.ToRealArray(dummyGy);

            y.Backward();


            Real[] cYdata = Real.ToRealArray((Real[, , , ])cY.Data.Copy());
            Real[] cXgrad = Real.ToRealArray((Real[, , , ])cX.Grad.Copy());

            Real[] cWgrad = Real.ToRealArray((Real[, , , ])cConvolotion2D.W.Grad);
            Real[] cbgrad = (Real[])cConvolotion2D.b.Grad;

            //許容範囲を算出
            double delta = 0.00001;

            Assert.AreEqual(cYdata.Length, y.Data.Length);
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);
            Assert.AreEqual(cWgrad.Length, convolution2D.Weight.Grad.Length);
            Assert.AreEqual(cbgrad.Length, convolution2D.Bias.Grad.Length);

            //y
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //x.grad
            for (int i = 0; i < x.Grad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }

            delta = 0.1;
            //W.grad
            for (int i = 0; i < convolution2D.Weight.Grad.Length; i++)
            {
                Assert.AreEqual(cWgrad[i], convolution2D.Weight.Grad[i], delta);
            }

            //b.grad
            for (int i = 0; i < convolution2D.Bias.Grad.Length; i++)
            {
                Assert.AreEqual(cbgrad[i], convolution2D.Bias.Grad[i], delta);
            }
        }
Beispiel #7
0
        public void LSTMRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int batchCount  = Mother.Dice.Next(1, 5);
            int inputCount  = Mother.Dice.Next(1, 5);
            int outputCount = Mother.Dice.Next(1, 5);

            Real[,] input   = Initializer.GetRandomValues <Real[, ]>(batchCount, inputCount);
            Real[,] dummyGy = Initializer.GetRandomValues <Real[, ]>(batchCount, outputCount);

            Real[,] upwardInit      = Initializer.GetRandomValues <Real[, ]>(outputCount, inputCount);
            Real[,] lateralInit     = Initializer.GetRandomValues <Real[, ]>(outputCount, outputCount);
            Real[,,] biasInit       = Initializer.GetRandomValues <Real[, , ]>(1, outputCount, 1);
            Real[,,] forgetBiasInit = Initializer.GetRandomValues <Real[, , ]>(1, outputCount, 1);

            //Chainer
            NChainer.LSTM <Real> clstm = new NChainer.LSTM <Real>(inputCount, outputCount, lateralInit, upwardInit, biasInit, forgetBiasInit);

            Variable <Real> cX = new Variable <Real>(input);
            Variable <Real> cY = clstm.Forward(cX);

            cY.Grad = dummyGy;

            cY.Backward();

            //KelpNet
            LSTM <Real> lstm = new LSTM <Real>(inputCount, outputCount, lateralInit, upwardInit, biasInit, forgetBiasInit);

            NdArray <Real> x = new NdArray <Real>(input, asBatch: true);
            NdArray <Real> y = lstm.Forward(x)[0];

            y.Grad = dummyGy.Flatten();

            y.Backward();

            //許容範囲を算出
            Real delta = 0.00001f;

            Real[] cYdata = ((Real[, ])cY.Data).Flatten();
            Real[] cXgrad = ((Real[, ])cX.Grad).Flatten();

            Real[] cupwardWGrad = ((Real[, ])clstm.upward.W.Grad).Flatten();
            Real[] cupwardbGrad = (Real[])clstm.upward.b.Grad;


            //y
            Assert.AreEqual(cYdata.Length, y.Data.Length);
            for (int i = 0; i < cYdata.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //x.Grad
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);
            for (int i = 0; i < cXgrad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }

            //W.grad
            int wLen = lstm.upward.Weight.Grad.Length;

            Assert.AreEqual(cupwardWGrad.Length, lstm.upward.Weight.Grad.Length);
            for (int i = 0; i < wLen; i++)
            {
                Assert.AreEqual(cupwardWGrad[i + wLen * 0], lstm.upward.Weight.Grad[i], delta);
            }

            //b.grad
            int bLen = lstm.upward.Bias.Length;

            Assert.AreEqual(cupwardbGrad.Length, lstm.upward.Bias.Grad.Length);
            for (int i = 0; i < bLen; i++)
            {
                Assert.AreEqual(cupwardbGrad[i + wLen * 0], lstm.upward.Bias.Grad[i], delta);
            }


            //////////////////////////////////////////////////////////////////////////////////////////
            // 1度目はlateralに値はない                                                             //
            //////////////////////////////////////////////////////////////////////////////////////////
            //Real[] clateralWGrad = Real.ToRealArray((Real[,])clstm.lateral.W.Grad);
            //Assert.AreEqual(clateralWGrad.Length, lstm.lateral.Weight.Grad.Length);
            //for (int i = 0; i < wLen; i++)
            //{
            //    Assert.AreEqual(clateralWGrad[i + wLen * 0], lstm.lateral.Weight.Grad[i], delta);
            //}
            //////////////////////////////////////////////////////////////////////////////////////////

            ///////////
            //2周目 //
            ///////////
            Real[,] input2   = Initializer.GetRandomValues <Real[, ]>(batchCount, inputCount);
            Real[,] dummyGy2 = Initializer.GetRandomValues <Real[, ]>(batchCount, outputCount);

            //Chainer
            Variable <Real> cX2 = new Variable <Real>(input2);
            Variable <Real> cY2 = clstm.Forward(cX2);

            cY2.Grad = dummyGy2;

            cY2.Backward();

            //KelpNet
            NdArray <Real> x2 = new NdArray <Real>(input2, asBatch: true);
            NdArray <Real> y2 = lstm.Forward(x2)[0];

            y2.Grad = dummyGy2.Flatten();

            y2.Backward();

            Real[] cYdata2 = ((Real[, ])cY2.Data).Flatten();
            Real[] cXgrad2 = ((Real[, ])cX2.Grad).Flatten();

            Real[] cupwardWGrad2 = ((Real[, ])clstm.upward.W.Grad).Flatten();
            Real[] cupwardbGrad2 = (Real[])clstm.upward.b.Grad;
            Real[] clateralWGrad = ((Real[, ])clstm.lateral.W.Grad).Flatten();

            //y
            Assert.AreEqual(cYdata2.Length, y2.Data.Length);
            for (int i = 0; i < cYdata2.Length; i++)
            {
                Assert.AreEqual(cYdata2[i], y2.Data[i], delta);
            }

            //x.Grad
            Assert.AreEqual(cXgrad2.Length, x2.Grad.Length);
            for (int i = 0; i < cXgrad2.Length; i++)
            {
                Assert.AreEqual(cXgrad2[i], x2.Grad[i], delta);
            }

            //W.grad
            Assert.AreEqual(clateralWGrad.Length, lstm.lateral.Weight.Grad.Length);
            for (int i = 0; i < clateralWGrad.Length; i++)
            {
                Assert.AreEqual(clateralWGrad[i + wLen * 0], lstm.lateral.Weight.Grad[i], delta);
            }

            //経由が多いため誤差が大きい
            delta = 1.0f;
            for (int i = 0; i < wLen; i++)
            {
                Assert.AreEqual(cupwardWGrad2[i + wLen * 0], lstm.upward.Weight.Grad[i], delta);
            }

            //b.grad
            for (int i = 0; i < bLen; i++)
            {
                Assert.AreEqual(cupwardbGrad2[i + wLen * 0], lstm.upward.Bias.Grad[i], delta);
            }
        }
        public void RnnLSTMRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            Real[,] input = { { 1.0 }, { 3.0 }, { 5.0 }, { 7.0 }, { 9.0 } };
            Real[,] teach = { { 3.0 }, { 5.0 }, { 7.0 }, { 9.0 }, { 11.0 } };

            Real[,] input2 = { { 3.0 }, { 5.0 }, { 7.0 }, { 9.0 }, { 11.0 } };
            Real[,] teach2 = { { 5.0 }, { 7.0 }, { 9.0 }, { 11.0 }, { 13.0 } };

            int outputCount = 1;
            int inputCount  = 1;
            int hiddenCount = 2;

            Real[,] upwardInit      = (Real[, ])Initializer.GetRealNdArray(new[] { hiddenCount, hiddenCount });
            Real[,] lateralInit     = (Real[, ])Initializer.GetRealNdArray(new[] { hiddenCount, hiddenCount });
            Real[,,] biasInit       = (Real[, , ])Initializer.GetRealNdArray(new[] { 1, hiddenCount, 1 });
            Real[,,] forgetBiasInit = (Real[, , ])Initializer.GetRealNdArray(new[] { 1, hiddenCount, 1 });

            //Chainer
            Real[,] w1 = (Real[, ])Initializer.GetRealNdArray(new[] { hiddenCount, inputCount });
            Real[] b1 = Initializer.GetRealArray(hiddenCount);

            //Chainer
            NChainer.Linear <Real> cLinear1 = new NChainer.Linear <Real>(inputCount, hiddenCount, false, Real.ToBaseNdArray(w1), Real.ToBaseArray(b1));
            NChainer.LSTM <Real>   cLstm    = new NChainer.LSTM <Real>(hiddenCount, hiddenCount, Real.ToBaseNdArray(lateralInit), Real.ToBaseNdArray(upwardInit), Real.ToBaseNdArray(biasInit), Real.ToBaseNdArray(forgetBiasInit));

            Real[,] w2 = (Real[, ])Initializer.GetRealNdArray(new[] { outputCount, hiddenCount });
            Real[] b2 = Initializer.GetRealArray(outputCount);
            NChainer.Linear <Real> cLinear2 = new NChainer.Linear <Real>(hiddenCount, outputCount, false, Real.ToBaseNdArray(w2), Real.ToBaseArray(b2));

            Variable <Real> cX1  = new Variable <Real>(Real.ToBaseNdArray(input));
            Variable <Real> cY11 = cLinear1.Forward(cX1);
            Variable <Real> cY12 = cLstm.Forward(cY11);
            Variable <Real> cY13 = cLinear2.Forward(cY12);
            Variable <Real> cT   = new Variable <Real>(Real.ToBaseNdArray(teach));

            Variable <Real> cLoss = new NChainer.MeanSquaredError <Real>().Forward(cY13, cT);

            cLoss.Backward();


            //KelpNet
            KelpNet.CL.Linear linear1 = new KelpNet.CL.Linear(inputCount, hiddenCount, false, w1, b1);
            KelpNet.LSTM      lstm    = new KelpNet.LSTM(hiddenCount, hiddenCount, lateralInit, upwardInit, biasInit, forgetBiasInit);
            KelpNet.CL.Linear linear2 = new KelpNet.CL.Linear(hiddenCount, outputCount, false, w2, b2);

            NdArray x1  = new NdArray(Real.ToRealArray(input), new[] { 1 }, 5);
            NdArray y11 = linear1.Forward(x1)[0];
            NdArray y12 = lstm.Forward(y11)[0];
            NdArray y13 = linear2.Forward(y12)[0];
            NdArray t   = new NdArray(Real.ToRealArray(teach), new[] { 1 }, 5);

            NdArray loss = new KelpNet.MeanSquaredError().Evaluate(y13, t);

            y13.Backward();

            Real[] cY11data = Real.ToRealArray((Real[, ])cY11.Data);
            Real[] cY12data = Real.ToRealArray((Real[, ])cY12.Data);
            Real[] cY13data = Real.ToRealArray((Real[, ])cY13.Data);
            Real[] cXgrad   = Real.ToRealArray((Real[, ])cX1.Grad);

            Real[] cupwardWGrad = Real.ToRealArray((Real[, ])cLstm.upward.W.Grad);
            Real[] cupwardbGrad = (Real[])cLstm.upward.b.Grad;


            //許容範囲を設定
            double delta = 0.00001;

            //y11
            Assert.AreEqual(cY11data.Length, y11.Data.Length);
            for (int i = 0; i < cY11data.Length; i++)
            {
                Assert.AreEqual(cY11data[i], y11.Data[i], delta);
            }

            //y12
            Assert.AreEqual(cY12data.Length, y12.Data.Length);
            for (int i = 0; i < cY12data.Length; i++)
            {
                Assert.AreEqual(cY12data[i], y12.Data[i], delta);
            }

            //y13
            Assert.AreEqual(cY13data.Length, y13.Data.Length);
            for (int i = 0; i < cY13data.Length; i++)
            {
                Assert.AreEqual(cY13data[i], y13.Data[i], delta);
            }

            //許容範囲を設定
            delta = 0.0001;

            //loss
            Assert.AreEqual(cLoss.Data[0], loss.Data[0], delta);

            //x.Grad
            Assert.AreEqual(cXgrad.Length, x1.Grad.Length);
            for (int i = 0; i < cXgrad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x1.Grad[i], delta);
            }

            Real[] cWgrad11 = Real.ToRealArray((Real[, ])cLinear1.W.Grad);
            Real[] cbgrad11 = (Real[])cLinear1.b.Grad;

            //W.grad
            Assert.AreEqual(cWgrad11.Length, linear1.Weight.Grad.Length);
            for (int i = 0; i < linear1.Weight.Grad.Length; i++)
            {
                Assert.AreEqual(cWgrad11[i], linear1.Weight.Grad[i], delta);
            }

            //b.grad
            Assert.AreEqual(cbgrad11.Length, linear1.Bias.Grad.Length);
            for (int i = 0; i < linear1.Bias.Grad.Length; i++)
            {
                Assert.AreEqual(cbgrad11[i], linear1.Bias.Grad[i], delta);
            }


            Real[] cWgrad12 = Real.ToRealArray((Real[, ])cLinear2.W.Grad);
            Real[] cbgrad12 = (Real[])cLinear2.b.Grad;


            //W.grad
            Assert.AreEqual(cWgrad12.Length, linear2.Weight.Grad.Length);
            for (int i = 0; i < linear2.Weight.Grad.Length; i++)
            {
                Assert.AreEqual(cWgrad12[i], linear2.Weight.Grad[i], delta);
            }

            //b.grad
            Assert.AreEqual(cbgrad12.Length, linear2.Bias.Grad.Length);
            for (int i = 0; i < linear2.Bias.Grad.Length; i++)
            {
                Assert.AreEqual(cbgrad12[i], linear2.Bias.Grad[i], delta);
            }

            //W.grad
            int wLen = lstm.upward.Weight.Grad.Length;

            Assert.AreEqual(cupwardWGrad.Length, lstm.upward.Weight.Grad.Length);
            for (int i = 0; i < wLen; i++)
            {
                Assert.AreEqual(cupwardWGrad[i + wLen * 0], lstm.upward.Weight.Grad[i], delta);
            }

            //b.grad
            int bLen = lstm.upward.Bias.Length;

            Assert.AreEqual(cupwardbGrad.Length, lstm.upward.Bias.Grad.Length);
            for (int i = 0; i < bLen; i++)
            {
                Assert.AreEqual(cupwardbGrad[i + wLen * 0], lstm.upward.Bias.Grad[i], delta);
            }


            //2周目
            Variable <Real> cX2  = new Variable <Real>(Real.ToBaseNdArray(input2));
            Variable <Real> cY21 = cLinear1.Forward(cX2);
            Variable <Real> cY22 = cLstm.Forward(cY21);
            Variable <Real> cY23 = cLinear2.Forward(cY22);
            Variable <Real> cT2  = new Variable <Real>(Real.ToBaseNdArray(teach2));

            Variable <Real> cLoss2 = new NChainer.MeanSquaredError <Real>().Forward(cY23, cT2);

            //KelpNet
            NdArray x2  = new NdArray(Real.ToRealArray(input2), new[] { 1 }, 5);
            NdArray y21 = linear1.Forward(x2)[0];
            NdArray y22 = lstm.Forward(y21)[0];
            NdArray y23 = linear2.Forward(y22)[0];
            NdArray t2  = new NdArray(Real.ToRealArray(teach2), new[] { 1 }, 5);

            NdArray loss2 = new KelpNet.MeanSquaredError().Evaluate(y23, t2);

            Assert.AreEqual(cLoss2.Data[0], loss2.Data[0], delta);

            //Backwardを実行
            cLoss2.Backward();
            y23.Backward();


            Real[] cYdata21 = Real.ToRealArray((Real[, ])cY21.Data);
            Real[] cYdata22 = Real.ToRealArray((Real[, ])cY22.Data);
            Real[] cYdata23 = Real.ToRealArray((Real[, ])cY23.Data);
            Real[] cXgrad2  = Real.ToRealArray((Real[, ])cX2.Grad);

            Real[] cupwardWGrad2 = Real.ToRealArray((Real[, ])cLstm.upward.W.Grad);
            Real[] cupwardbGrad2 = (Real[])cLstm.upward.b.Grad;
            Real[] clateralWGrad = Real.ToRealArray((Real[, ])cLstm.lateral.W.Grad);

            //y21
            Assert.AreEqual(cYdata21.Length, y21.Data.Length);
            for (int i = 0; i < cYdata21.Length; i++)
            {
                Assert.AreEqual(cYdata21[i], y21.Data[i], delta);
            }

            //y22
            Assert.AreEqual(cYdata22.Length, y22.Data.Length);
            for (int i = 0; i < cYdata22.Length; i++)
            {
                Assert.AreEqual(cYdata22[i], y22.Data[i], delta);
            }

            //y23
            Assert.AreEqual(cYdata23.Length, y23.Data.Length);
            for (int i = 0; i < cYdata23.Length; i++)
            {
                Assert.AreEqual(cYdata23[i], y23.Data[i], delta);
            }

            //x.Grad
            Assert.AreEqual(cXgrad2.Length, x2.Grad.Length);
            for (int i = 0; i < cXgrad2.Length; i++)
            {
                Assert.AreEqual(cXgrad2[i], x2.Grad[i], delta);
            }

            //経由が多くかなり誤差が大きい為
            delta = 1.0;

            Real[] cWgrad22 = Real.ToRealArray((Real[, ])cLinear2.W.Grad);
            Real[] cbgrad22 = (Real[])cLinear2.b.Grad;

            //W.grad
            Assert.AreEqual(cWgrad22.Length, linear2.Weight.Grad.Length);
            for (int i = 0; i < linear2.Weight.Grad.Length; i++)
            {
                Assert.AreEqual(cWgrad22[i], linear2.Weight.Grad[i], delta);
            }

            //b.grad
            Assert.AreEqual(cbgrad22.Length, linear2.Bias.Grad.Length);
            for (int i = 0; i < linear2.Bias.Grad.Length; i++)
            {
                Assert.AreEqual(cbgrad22[i], linear2.Bias.Grad[i], delta);
            }


            delta = 2.0;

            //W.grad
            Assert.AreEqual(clateralWGrad.Length, lstm.lateral.Weight.Grad.Length);
            for (int i = 0; i < clateralWGrad.Length; i++)
            {
                Assert.AreEqual(clateralWGrad[i + wLen * 0], lstm.lateral.Weight.Grad[i], delta);
            }

            for (int i = 0; i < wLen; i++)
            {
                Assert.AreEqual(cupwardWGrad2[i + wLen * 0], lstm.upward.Weight.Grad[i], delta);
            }

            //b.grad
            for (int i = 0; i < bLen; i++)
            {
                Assert.AreEqual(cupwardbGrad2[i + wLen * 0], lstm.upward.Bias.Grad[i], delta);
            }


            delta = 20.0;

            Real[] cWgrad21 = Real.ToRealArray((Real[, ])cLinear1.W.Grad);
            Real[] cbgrad21 = (Real[])cLinear1.b.Grad;

            //W.grad
            Assert.AreEqual(cWgrad21.Length, linear1.Weight.Grad.Length);
            for (int i = 0; i < linear1.Weight.Grad.Length; i++)
            {
                Assert.AreEqual(cWgrad21[i], linear1.Weight.Grad[i], delta);
            }

            //b.grad
            Assert.AreEqual(cbgrad21.Length, linear1.Bias.Grad.Length);
            for (int i = 0; i < linear1.Bias.Grad.Length; i++)
            {
                Assert.AreEqual(cbgrad21[i], linear1.Bias.Grad[i], delta);
            }
        }
Beispiel #9
0
 //Backward
 public void BackwardFS(params NdArray <T>[] ys)
 {
     NdArray.Backward(ys[0]);
 }
Beispiel #10
0
        public void LRNRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int   n = Mother.Dice.Next(2, 7);
            float k = (float)Mother.Dice.NextDouble() * 3;

            int batchCount = Mother.Dice.Next(1, 5);
            int ch         = Mother.Dice.Next(1, 5);
            int width      = Mother.Dice.Next(1, 16);
            int height     = Mother.Dice.Next(1, 16);

            Real[,,,] input   = Initializer.GetRandomValues <Real[, , , ]>(batchCount, ch, height, width);
            Real[,,,] dummyGy = Initializer.GetRandomValues <Real[, , , ]>(batchCount, ch, height, width);


            //chainer
            LocalResponseNormalization <Real> cLocalResponseNormalization = new LocalResponseNormalization <Real>(n, k);

            Variable <Real> cX = new Variable <Real>(input);

            Variable <Real> cY = cLocalResponseNormalization.Forward(cX);

            cY.Grad = dummyGy;

            cY.Backward();


            //kelpnet
            LRN <Real> lrn = new LRN <Real>(n, k);

            NdArray <Real> x = new NdArray <Real>(input, asBatch: true);

            NdArray <Real> y = lrn.Forward(x)[0];

            y.Grad = dummyGy.Flatten();

            y.Backward();


            Real[] cYdata = ((Real[, , , ])cY.Data).Flatten();
            Real[] cXgrad = ((Real[, , , ])cX.Grad).Flatten();

            //許容範囲を算出
            Real delta = 0.00001f;

            //y
            Assert.AreEqual(cYdata.Length, y.Data.Length);
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //x.grad
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);
            for (int i = 0; i < x.Grad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }
        }
Beispiel #11
0
        public void SwishRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int ioCount    = Mother.Dice.Next(1, 50);
            int batchCount = Mother.Dice.Next(1, 5);

            Real[,] input = Initializer.GetRandomValues <Real[, ]>(batchCount, ioCount);

            Real[,] dummyGy = Initializer.GetRandomValues <Real[, ]>(batchCount, ioCount);

            Real beta = (Real)Mother.Dice.NextDouble();

            //Chainer
            NChainer.Swish <Real> cSwish = new NChainer.Swish <Real>(new[] { ioCount }, beta);

            Variable <Real> cX = new Variable <Real>(input);

            Variable <Real> cY = cSwish.Forward(cX);

            cY.Grad = dummyGy;

            cY.Backward();


            //KelpNet
            Swish <Real> swish = new Swish <Real>(new[] { ioCount }, beta);

            NdArray <Real> x = new NdArray <Real>(input, asBatch: true);

            NdArray <Real> y = swish.Forward(x)[0];

            y.Grad = dummyGy.Flatten();

            y.Backward();


            Real[] cYdata = ((Real[, ])cY.Data).Flatten();
            Real[] cXgrad = ((Real[, ])cX.Grad).Flatten();

            Real[] cbgrad = (Real[])cSwish.beta.Grad;

            //許容範囲を算出
            Real delta = 0.00001f;

            //y
            Assert.AreEqual(cYdata.Length, y.Data.Length);
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //x.grad
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);
            for (int i = 0; i < x.Grad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }

            //b.grad
            Assert.AreEqual(cbgrad.Length, swish.Beta.Grad.Length);
            for (int i = 0; i < swish.Beta.Grad.Length; i++)
            {
                Assert.AreEqual(cbgrad[i], swish.Beta.Grad[i], delta);
            }
        }
        public void TrainTest(bool isTtrain, bool finetune)
        {
            Python.Initialize();
            Chainer.Initialize();

            int batchCount = Mother.Dice.Next(1, 50);
            int ioCount    = Mother.Dice.Next(1, 50);

            Real[,] input = (Real[, ])Initializer.GetRealNdArray(new[] { batchCount, ioCount });

            Real[,] dummyGy = (Real[, ])Initializer.GetRealNdArray(new[] { batchCount, ioCount });

            Real[] gamma = Initializer.GetRealArray(ioCount);
            Real[] beta  = Initializer.GetRealArray(ioCount);

            Real[] avgMean = Initializer.GetRealArray(ioCount);
            Real[] avgVar  = Initializer.GetRealArray(ioCount);

            //Chainer
            Chainer.Config["train"] = isTtrain;

            NChainer.BatchNormalization <Real> cBatchNormalization = new NChainer.BatchNormalization <Real>(ioCount, dtype: Real.Type);

            cBatchNormalization.gamma = new Variable <Real>(Real.ToBaseNdArray(gamma));
            cBatchNormalization.beta  = new Variable <Real>(Real.ToBaseNdArray(beta));

            cBatchNormalization.avgMean = Real.ToBaseNdArray(avgMean);
            cBatchNormalization.avgVar  = Real.ToBaseNdArray(avgVar);

            Variable <Real> cX = new Variable <Real>(Real.ToBaseNdArray(input));

            Variable <Real> cY = cBatchNormalization.Forward(cX, finetune);

            cY.Grad = Real.ToBaseNdArray(dummyGy);

            cY.Backward();

            //KelpNet
            KelpNet.BatchNormalization batchNormalization = new BatchNormalization(ioCount, train: isTtrain, finetune: finetune);

            batchNormalization.Gamma.Data = Real.ToRealArray(gamma);
            batchNormalization.Beta.Data  = Real.ToRealArray(beta);

            batchNormalization.AvgMean.Data = Real.ToRealArray(avgMean);
            batchNormalization.AvgVar.Data  = Real.ToRealArray(avgVar);

            NdArray x = new NdArray(Real.ToRealArray(input), new[] { ioCount }, batchCount);

            NdArray y = batchNormalization.Forward(x)[0];

            y.Grad = Real.ToRealArray(dummyGy);

            y.Backward();


            Real[] cYdata = Real.ToRealArray((Real[, ])cY.Data);
            Real[] cXgrad = Real.ToRealArray((Real[, ])cX.Grad);

            Real[] cGammaGrad = Real.ToRealArray((Real[])cBatchNormalization.gamma.Grad);
            Real[] cBetaGrad  = Real.ToRealArray((Real[])cBatchNormalization.beta.Grad);

            //許容範囲を算出
            double delta = 0.00001;

            //y
            Assert.AreEqual(cYdata.Length, y.Data.Length);
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //x.grad
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);
            for (int i = 0; i < x.Grad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }

            //gamma.grad
            Assert.AreEqual(cGammaGrad.Length, batchNormalization.Gamma.Grad.Length);
            for (int i = 0; i < batchNormalization.Gamma.Grad.Length; i++)
            {
                Assert.AreEqual(cGammaGrad[i], batchNormalization.Gamma.Grad[i], delta);
            }

            //beta.grad
            Assert.AreEqual(cBetaGrad.Length, batchNormalization.Beta.Grad.Length);
            for (int i = 0; i < batchNormalization.Beta.Grad.Length; i++)
            {
                Assert.AreEqual(cBetaGrad[i], batchNormalization.Beta.Grad[i], delta);
            }
        }
Beispiel #13
0
        public void ConcatRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int batchCount = Mother.Dice.Next(1, 5);
            int ch         = Mother.Dice.Next(1, 5);
            int widthA     = Mother.Dice.Next(1, 16);
            int widthB     = Mother.Dice.Next(1, 16);
            int height     = Mother.Dice.Next(1, 16);
            int axis       = 3;

            Real[,,,] inputA  = (Real[, , , ])Initializer.GetRealNdArray(new[] { batchCount, ch, height, widthA });
            Real[,,,] inputB  = (Real[, , , ])Initializer.GetRealNdArray(new[] { batchCount, ch, height, widthB });
            Real[,,,] dummyGy = (Real[, , , ])Initializer.GetRealNdArray(new[] { batchCount, ch, height, widthA + widthB });

            //chainer
            NChainer.Concat <Real> cConcat = new NChainer.Concat <Real>(axis);

            Variable <Real> cX = new Variable <Real>(Real.ToBaseNdArray(inputA));
            Variable <Real> cY = new Variable <Real>(Real.ToBaseNdArray(inputB));

            Variable <Real> cZ = cConcat.Forward(cX, cY);

            cZ.Grad = Real.ToBaseNdArray(dummyGy);

            cZ.Backward();


            //KelpNet
            KelpNet.Concat concat = new Concat(axis - 1);//Chainerと異なり1次元目を暗黙的にBatchとみなさないため

            NdArray x = new NdArray(Real.ToRealArray(inputA), new[] { ch, height, widthA }, batchCount);
            NdArray y = new NdArray(Real.ToRealArray(inputB), new[] { ch, height, widthB }, batchCount);

            NdArray z = concat.Forward(x, y)[0];

            z.Grad = Real.ToRealArray(dummyGy);

            z.Backward();


            Real[] cZdata = Real.ToRealArray((Real[, , , ])cZ.Data);

            //Copyが必要
            Real[] cXgrad = Real.ToRealArray((Real[, , , ])cX.Grad.Copy());
            Real[] cYgrad = Real.ToRealArray((Real[, , , ])cY.Grad.Copy());

            //許容範囲を算出
            double delta = 0.00001;

            //z
            Assert.AreEqual(cZdata.Length, z.Data.Length);
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cZdata[i], z.Data[i], delta);
            }

            //x.grad
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);
            for (int i = 0; i < x.Grad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }

            //y.grad
            Assert.AreEqual(cYgrad.Length, y.Grad.Length);
            for (int i = 0; i < y.Grad.Length; i++)
            {
                Assert.AreEqual(cYgrad[i], y.Grad[i], delta);
            }
        }
Beispiel #14
0
        public void AVGPoolingRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int batchCount = Mother.Dice.Next(1, 5);
            int chCount    = Mother.Dice.Next(1, 5);
            int wideSize   = Mother.Dice.Next(8, 32);
            int heightSize = Mother.Dice.Next(8, 32);

            int kWidth  = Mother.Dice.Next(1, 5);
            int kHeight = Mother.Dice.Next(1, 5);

            int strideX = Mother.Dice.Next(1, 5);
            int strideY = Mother.Dice.Next(1, 5);

            int padX = Mother.Dice.Next(0, 5);
            int padY = Mother.Dice.Next(0, 5);


            int outputHeight = (int)Math.Floor((heightSize - kHeight + padY * 2.0f) / strideY) + 1;

            int outputWidth = (int)Math.Floor((wideSize - kWidth + padX * 2.0f) / strideX) + 1;

            Real[,,,] input = Initializer.GetRandomValues <Real[, , , ]>(batchCount, chCount, heightSize, wideSize);

            Real[,,,] dummyGy = Initializer.GetRandomValues <Real[, , , ]>(batchCount, chCount, outputHeight, outputWidth);

            //Chainer
            NChainer.AveragePooling2D <Real> cMaxPooling2D = new NChainer.AveragePooling2D <Real>(
                new[] { kHeight, kWidth },
                new[] { strideY, strideX },
                new[] { padY, padX }
                );

            Variable <Real> cX = new Variable <Real>(input);

            Variable <Real> cY = cMaxPooling2D.Forward(cX);

            cY.Grad = dummyGy;

            cY.Backward();


            //KelpNet
            KelpNet.AveragePooling2D <Real> maxPooling2D = new KelpNet.AveragePooling2D <Real>(
                new[] { kWidth, kHeight },
                new[] { strideX, strideY },
                new[] { padX, padY });

            NdArray <Real> x = new NdArray <Real>(input, asBatch: true);

            NdArray <Real> y = maxPooling2D.Forward(x)[0];

            y.Grad = dummyGy.Flatten();

            y.Backward();

            Real[] cYdata = ((Real[, , , ])cY.Data.Copy()).Flatten();
            Real[] cXgrad = ((Real[, , , ])cX.Grad.Copy()).Flatten();

            //許容範囲を算出
            Real delta = 0.00001f;

            Assert.AreEqual(cYdata.Length, y.Data.Length);
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);

            //y
            for (int i = 0; i < y.Data.Length; i++)
            {
                if (cYdata[i] < float.Epsilon && cYdata[i] > -float.Epsilon)
                {
                    Assert.AreEqual(cYdata[i], y.Data[i], delta);
                }
            }

            //x.grad
            for (int i = 0; i < x.Grad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }
        }
Beispiel #15
0
        public void LSTMRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int batchCount  = Mother.Dice.Next(1, 5);
            int inputCount  = Mother.Dice.Next(1, 5);
            int outputCount = Mother.Dice.Next(1, 5);

            Real[,] input   = (Real[, ])Initializer.GetRealNdArray(new[] { batchCount, inputCount });
            Real[,] dummyGy = (Real[, ])Initializer.GetRealNdArray(new[] { batchCount, outputCount });

            Real[,] upwardInit      = (Real[, ])Initializer.GetRealNdArray(new[] { outputCount, inputCount });
            Real[,] lateralInit     = (Real[, ])Initializer.GetRealNdArray(new[] { outputCount, outputCount });
            Real[,,] biasInit       = (Real[, , ])Initializer.GetRealNdArray(new[] { 1, outputCount, 1 });
            Real[,,] forgetBiasInit = (Real[, , ])Initializer.GetRealNdArray(new[] { 1, outputCount, 1 });

            //Chainer
            NChainer.LSTM <Real> clstm = new NChainer.LSTM <Real>(inputCount, outputCount, Real.ToBaseNdArray(lateralInit), Real.ToBaseNdArray(upwardInit), Real.ToBaseNdArray(biasInit), Real.ToBaseNdArray(forgetBiasInit));

            Variable <Real> cX = new Variable <Real>(Real.ToBaseNdArray(input));
            Variable <Real> cY = clstm.Forward(cX);

            cY.Grad = Real.ToBaseNdArray(dummyGy);

            cY.Backward();

            //KelpNet
            KelpNet.LSTM lstm = new KelpNet.LSTM(inputCount, outputCount, lateralInit, upwardInit, biasInit, forgetBiasInit);

            NdArray x = new NdArray(Real.ToRealArray(input), new[] { inputCount }, batchCount);
            NdArray y = lstm.Forward(x)[0];

            y.Grad = Real.ToRealArray(dummyGy);

            y.Backward();

            //許容範囲を算出
            double delta = 0.00001;

            Real[] cYdata = Real.ToRealArray((Real[, ])cY.Data);
            Real[] cXgrad = Real.ToRealArray((Real[, ])cX.Grad);

            Real[] cupwardWGrad = Real.ToRealArray((Real[, ])clstm.upward.W.Grad);
            Real[] cupwardbGrad = (Real[])clstm.upward.b.Grad;


            //y
            Assert.AreEqual(cYdata.Length, y.Data.Length);
            for (int i = 0; i < cYdata.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //x.Grad
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);
            for (int i = 0; i < cXgrad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }

            //W.grad
            int wLen = lstm.upward.Weight.Grad.Length;

            Assert.AreEqual(cupwardWGrad.Length, lstm.upward.Weight.Grad.Length);
            for (int i = 0; i < wLen; i++)
            {
                Assert.AreEqual(cupwardWGrad[i + wLen * 0], lstm.upward.Weight.Grad[i], delta);
            }

            //b.grad
            int bLen = lstm.upward.Bias.Length;

            Assert.AreEqual(cupwardbGrad.Length, lstm.upward.Bias.Grad.Length);
            for (int i = 0; i < bLen; i++)
            {
                Assert.AreEqual(cupwardbGrad[i + wLen * 0], lstm.upward.Bias.Grad[i], delta);
            }


            //////////////////////////////////////////////////////////////////////////////////////////
            // 1度目はlateralに値はない                                                             //
            //////////////////////////////////////////////////////////////////////////////////////////
            //Real[] clateralWGrad = Real.ToRealArray((Real[,])clstm.lateral.W.Grad);
            //Assert.AreEqual(clateralWGrad.Length, lstm.lateral.Weight.Grad.Length);
            //for (int i = 0; i < wLen; i++)
            //{
            //    Assert.AreEqual(clateralWGrad[i + wLen * 0], lstm.lateral.Weight.Grad[i], delta);
            //}
            //////////////////////////////////////////////////////////////////////////////////////////

            ///////////
            //2周目 //
            ///////////
            Real[,] input2   = (Real[, ])Initializer.GetRealNdArray(new[] { batchCount, inputCount });
            Real[,] dummyGy2 = (Real[, ])Initializer.GetRealNdArray(new[] { batchCount, outputCount });

            //Chainer
            Variable <Real> cX2 = new Variable <Real>(Real.ToBaseNdArray(input2));
            Variable <Real> cY2 = clstm.Forward(cX2);

            cY2.Grad = Real.ToBaseNdArray(dummyGy2);

            cY2.Backward();

            //KelpNet
            NdArray x2 = new NdArray(Real.ToRealArray(input2), new[] { inputCount }, batchCount);
            NdArray y2 = lstm.Forward(x2)[0];

            y2.Grad = Real.ToRealArray(dummyGy2);

            y2.Backward();

            Real[] cYdata2 = Real.ToRealArray((Real[, ])cY2.Data);
            Real[] cXgrad2 = Real.ToRealArray((Real[, ])cX2.Grad);

            Real[] cupwardWGrad2 = Real.ToRealArray((Real[, ])clstm.upward.W.Grad);
            Real[] cupwardbGrad2 = (Real[])clstm.upward.b.Grad;
            Real[] clateralWGrad = Real.ToRealArray((Real[, ])clstm.lateral.W.Grad);

            //y
            Assert.AreEqual(cYdata2.Length, y2.Data.Length);
            for (int i = 0; i < cYdata2.Length; i++)
            {
                Assert.AreEqual(cYdata2[i], y2.Data[i], delta);
            }

            //x.Grad
            Assert.AreEqual(cXgrad2.Length, x2.Grad.Length);
            for (int i = 0; i < cXgrad2.Length; i++)
            {
                Assert.AreEqual(cXgrad2[i], x2.Grad[i], delta);
            }

            //W.grad
            Assert.AreEqual(clateralWGrad.Length, lstm.lateral.Weight.Grad.Length);
            for (int i = 0; i < clateralWGrad.Length; i++)
            {
                Assert.AreEqual(clateralWGrad[i + wLen * 0], lstm.lateral.Weight.Grad[i], delta);
            }

            //経由が多いため誤差が大きい
            delta = 1.0;
            for (int i = 0; i < wLen; i++)
            {
                Assert.AreEqual(cupwardWGrad2[i + wLen * 0], lstm.upward.Weight.Grad[i], delta);
            }

            //b.grad
            for (int i = 0; i < bLen; i++)
            {
                Assert.AreEqual(cupwardbGrad2[i + wLen * 0], lstm.upward.Bias.Grad[i], delta);
            }
        }
Beispiel #16
0
        public void BasicMathRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            //Make random value.
            Real[] val = { 1 + Mother.Dice.Next() };

            //Chainer
            Variable <Real> cX = new Variable <Real>(val);

            //Add
            Variable <Real> cAdd = 2 + cX + cX + 2;

            cAdd.Backward();
            Real[] pyGadd = (Real[])cX.Grad;

            //Mul
            Variable <Real> cMul = 2 * cX * cX * 3;

            cMul.Backward();
            Real[] pyGmul = (Real[])cX.Grad;

            //Sub
            Variable <Real> cSub = 30 - cX - cX - 2;

            cSub.Backward();
            Real[] pyGsub = (Real[])cX.Grad;

            //Div
            Variable <Real> cDiv = 50 / cX / cX / 2;

            cDiv.Backward();
            Real[] pyGdiv = (Real[])cX.Grad;


            //KelpNet
            NdArray <Real> x = new NdArray <Real>(val);

            //Add
            NdArray <Real> add = 2 + x + x + 2;

            add.Backward();
            Real[] gadd = x.Grad.ToArray(); //このToArrayはコピーのため

            //mul
            NdArray <Real> mul = 2 * x * x * 3;

            mul.Backward();
            Real[] gmul = x.Grad.ToArray();

            //sub
            NdArray <Real> sub = 30 - x - x - 2;

            sub.Backward();
            Real[] gsub = x.Grad.ToArray();

            //mul
            NdArray <Real> div = 50 / x / x / 2;

            div.Backward();
            Real[] gdiv = x.Grad.ToArray();


            //Check
            CollectionAssert.AreEqual(pyGadd, gadd);
            CollectionAssert.AreEqual(pyGmul, gmul);
            CollectionAssert.AreEqual(pyGsub, gsub);
            CollectionAssert.AreEqual(pyGdiv, gdiv);
        }
Beispiel #17
0
        public void AdamRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int inputCount  = Mother.Dice.Next(2, 50);
            int outputCount = Mother.Dice.Next(2, 50);
            int batchCount  = Mother.Dice.Next(1, 5);

            Real[,] input   = Initializer.GetRandomValues <Real[, ]>(batchCount, inputCount);
            Real[,] dummyGy = Initializer.GetRandomValues <Real[, ]>(batchCount, outputCount);
            Real[,] w       = Initializer.GetRandomValues <Real[, ]>(outputCount, inputCount);
            Real[] b = Initializer.GetRandomValues <Real[]>(outputCount);


            float alpha = (float)Mother.Dice.NextDouble(); //0.001f
            float beta1 = (float)Mother.Dice.NextDouble(); //0.9f;
            float beta2 = (float)Mother.Dice.NextDouble(); //0.999f;
            float eps   = (float)Mother.Dice.NextDouble(); //1e-08f;
            float eta   = (float)Mother.Dice.NextDouble(); //1.0f;

            //Chainer
            NChainer.Linear <Real> cLinear = new NChainer.Linear <Real>(inputCount, outputCount, false, w, b);
            NChainer.Adam <Real>   cAdam   = new NChainer.Adam <Real>(alpha, beta1, beta2, eps, eta);
            cAdam.Setup(cLinear);

            Variable <Real> cX = new Variable <Real>(input);

            Variable <Real> cY = cLinear.Forward(cX);

            cY.Grad = dummyGy;

            cY.Backward();

            cAdam.Update();

            //KelpNet
            KelpNet.CL.Linear <Real> linear = new KelpNet.CL.Linear <Real>(inputCount, outputCount, false, w, b);
            KelpNet.Adam <Real>      adam   = new Adam <Real>(alpha, beta1, beta2, eps, eta);
            adam.SetUp(linear);

            NdArray <Real> x = new NdArray <Real>(input, asBatch: true);

            NdArray <Real> y = linear.Forward(x)[0];

            y.Grad = dummyGy.Flatten();

            y.Backward();

            adam.Update();


            Real[] cW = ((Real[, ])cLinear.W.Data).Flatten();
            Real[] cb = (Real[])cLinear.b.Data;

            //許容範囲を算出
            Real delta = 0.00001f;

            //W.grad
            Assert.AreEqual(cW.Length, linear.Weight.Data.Length);
            for (int i = 0; i < linear.Weight.Data.Length; i++)
            {
                Assert.AreEqual(cW[i], linear.Weight.Data[i], delta);
            }

            //b.grad
            Assert.AreEqual(cb.Length, linear.Bias.Data.Length);
            for (int i = 0; i < linear.Bias.Data.Length; i++)
            {
                Assert.AreEqual(cb[i], linear.Bias.Data[i], delta);
            }
        }
Beispiel #18
0
        public void ConcatRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int batchCount = Mother.Dice.Next(1, 5);
            int ch         = Mother.Dice.Next(1, 5);
            int widthA     = Mother.Dice.Next(1, 16);
            int widthB     = Mother.Dice.Next(1, 16);
            int height     = Mother.Dice.Next(1, 16);
            int axis       = 3;

            Real[,,,] inputA  = Initializer.GetRandomValues <Real[, , , ]>(batchCount, ch, height, widthA);
            Real[,,,] inputB  = Initializer.GetRandomValues <Real[, , , ]>(batchCount, ch, height, widthB);
            Real[,,,] dummyGy = Initializer.GetRandomValues <Real[, , , ]>(batchCount, ch, height, widthA + widthB);

            //chainer
            NChainer.Concat <Real> cConcat = new NChainer.Concat <Real>(axis);

            Variable <Real> cX = new Variable <Real>(inputA);
            Variable <Real> cY = new Variable <Real>(inputB);

            Variable <Real> cZ = cConcat.Forward(cX, cY);

            cZ.Grad = dummyGy;

            cZ.Backward();


            //KelpNet
            Concat <Real> concat = new Concat <Real>(axis - 1);//Chainerと異なり1次元目を暗黙的にBatchとみなさないため

            NdArray <Real> x = new NdArray <Real>(inputA, asBatch: true);
            NdArray <Real> y = new NdArray <Real>(inputB, asBatch: true);

            NdArray <Real> z = concat.Forward(x, y)[0];

            z.Grad = dummyGy.Flatten();

            z.Backward();


            Real[] cZdata = ((Real[, , , ])cZ.Data).Flatten();

            //Copyが必要
            Real[] cXgrad = ((Real[, , , ])cX.Grad.Copy()).Flatten();
            Real[] cYgrad = ((Real[, , , ])cY.Grad.Copy()).Flatten();

            //許容範囲を算出
            Real delta = 0.00001f;

            //z
            Assert.AreEqual(cZdata.Length, z.Data.Length);
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cZdata[i], z.Data[i], delta);
            }

            //x.grad
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);
            for (int i = 0; i < x.Grad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }

            //y.grad
            Assert.AreEqual(cYgrad.Length, y.Grad.Length);
            for (int i = 0; i < y.Grad.Length; i++)
            {
                Assert.AreEqual(cYgrad[i], y.Grad[i], delta);
            }
        }
Beispiel #19
0
        public void SwishRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int ioCount = Mother.Dice.Next(1, 50);
            int batchCount = Mother.Dice.Next(1, 5);

            Real[,] input = (Real[,])Initializer.GetRealNdArray(new[] { batchCount, ioCount });

            Real[,] dummyGy = (Real[,])Initializer.GetRealNdArray(new[] { batchCount, ioCount });

            Real beta = Mother.Dice.NextDouble();

            //Chainer
            NChainer.Swish<Real> cSwish = new NChainer.Swish<Real>(new[] { ioCount }, beta);

            Variable<Real> cX = new Variable<Real>(Real.ToBaseNdArray(input));

            Variable<Real> cY = cSwish.Forward(cX);
            cY.Grad = Real.ToBaseNdArray(dummyGy);

            cY.Backward();


            //KelpNet
            KelpNet.Swish swish = new KelpNet.Swish(new[] { ioCount }, beta);

            NdArray x = new NdArray(Real.ToRealArray(input), new[] { ioCount }, batchCount);

            NdArray y = swish.Forward(x)[0];
            y.Grad = Real.ToRealArray(dummyGy);

            y.Backward();


            Real[] cYdata = Real.ToRealArray((Real[,])cY.Data);
            Real[] cXgrad = Real.ToRealArray((Real[,])cX.Grad);

            Real[] cbgrad = (Real[])cSwish.beta.Grad;

            //許容範囲を算出
            double delta = 0.00001;

            //y
            Assert.AreEqual(cYdata.Length, y.Data.Length);
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //x.grad
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);
            for (int i = 0; i < x.Grad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }

            //b.grad
            Assert.AreEqual(cbgrad.Length, swish.Beta.Grad.Length);
            for (int i = 0; i < swish.Beta.Grad.Length; i++)
            {
                Assert.AreEqual(cbgrad[i], swish.Beta.Grad[i], delta);
            }
        }
Beispiel #20
0
        public void SGDRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int inputCount  = Mother.Dice.Next(2, 50);
            int outputCount = Mother.Dice.Next(2, 50);
            int batchCount  = Mother.Dice.Next(1, 5);

            Real[,] input = Initializer.GetRandomValues <Real[, ]>(batchCount, inputCount);

            Real[,] dummyGy = Initializer.GetRandomValues <Real[, ]>(batchCount, outputCount);
            Real[,] w       = Initializer.GetRandomValues <Real[, ]>(outputCount, inputCount);

            Real[] b = Initializer.GetRandomValues <Real[]>(outputCount);

            //Chainer
            Linear <Real> cLinear = new Linear <Real>(inputCount, outputCount, false, w, b);

            NChainer.SGD <Real> cSgd = new NChainer.SGD <Real>();
            cSgd.Setup(cLinear);

            Variable <Real> cX = new Variable <Real>(input);

            Variable <Real> cY = cLinear.Forward(cX);

            cY.Grad = dummyGy;

            cY.Backward();

            cSgd.Update();

            //KelpNet
            CL.Linear <Real>   linear = new CL.Linear <Real>(inputCount, outputCount, false, w, b);
            KelpNet.SGD <Real> sgd    = new SGD <Real>();
            sgd.SetUp(linear);

            NdArray <Real> x = new NdArray <Real>(input, asBatch: true);

            NdArray <Real> y = linear.Forward(x)[0];

            y.Grad = dummyGy.Flatten();

            y.Backward();

            sgd.Update();


            Real[] cW = ((Real[, ])cLinear.W.Data).Flatten();
            Real[] cb = (Real[])cLinear.b.Data;

            //許容範囲を算出
            Real delta = 0.00001f;

            //W.grad
            Assert.AreEqual(cW.Length, linear.Weight.Data.Length);
            for (int i = 0; i < linear.Weight.Data.Length; i++)
            {
                Assert.AreEqual(cW[i], linear.Weight.Data[i], delta);
            }

            //b.grad
            Assert.AreEqual(cb.Length, linear.Bias.Data.Length);
            for (int i = 0; i < linear.Bias.Data.Length; i++)
            {
                Assert.AreEqual(cb[i], linear.Bias.Data[i], delta);
            }
        }
Beispiel #21
0
        public void RandomTest(bool gpuEnable)
        {
            Python.Initialize();
            Chainer.Initialize();

            int batchCount = Mother.Dice.Next(1, 5);
            int inChCount  = Mother.Dice.Next(1, 5);
            int outChCount = Mother.Dice.Next(1, 5);
            int wideSize   = Mother.Dice.Next(8, 32);
            int heightSize = Mother.Dice.Next(8, 32);

            int kWidth  = Mother.Dice.Next(1, 5);
            int kHeight = Mother.Dice.Next(1, 5);

            int strideX = Mother.Dice.Next(1, 5);
            int strideY = Mother.Dice.Next(1, 5);

            int padX = Mother.Dice.Next(0, 5);
            int padY = Mother.Dice.Next(0, 5);

            int outputHeight = (int)Math.Floor((heightSize - kHeight + padY * 2.0f) / strideY) + 1;
            int outputWidth  = (int)Math.Floor((wideSize - kWidth + padX * 2.0f) / strideX) + 1;

            Real[,,,] input = Initializer.GetRandomValues <Real[, , , ]>(batchCount, inChCount, heightSize, wideSize);

            Real[,,,] dummyGy = Initializer.GetRandomValues <Real[, , , ]>(batchCount, outChCount, outputHeight, outputWidth);
            Real[,,,] w       = Initializer.GetRandomValues <Real[, , , ]>(outChCount, inChCount, kHeight, kWidth);

            Real[] b = Initializer.GetRandomValues <Real[]>(outChCount);

            //Chainer
            NChainer.Convolution2D <Real> cConvolotion2D = new NChainer.Convolution2D <Real>(
                inChCount, outChCount,
                new[] { kHeight, kWidth },
                new[] { strideY, strideX },
                new[] { padY, padX },
                false,
                w,
                b);

            Variable <Real> cX = new Variable <Real>(input);

            Variable <Real> cY = cConvolotion2D.Forward(cX);

            cY.Grad = dummyGy;

            cY.Backward();


            //KelpNet
            CL.Convolution2D <Real> convolution2D = new CL.Convolution2D <Real>(
                inChCount, outChCount,
                new[] { kWidth, kHeight },
                new[] { strideX, strideY },
                new[] { padX, padY },
                false, w, b, gpuEnable: gpuEnable);

            NdArray <Real> x = new NdArray <Real>(input, asBatch: true);

            NdArray <Real> y = convolution2D.Forward(x)[0];

            y.Grad = dummyGy.Flatten();

            y.Backward();


            Real[] cYdata = ((Real[, , , ])cY.Data.Copy()).Flatten();
            Real[] cXgrad = ((Real[, , , ])cX.Grad.Copy()).Flatten();

            Real[] cWgrad = ((Real[, , , ])cConvolotion2D.W.Grad).Flatten();
            Real[] cbgrad = (Real[])cConvolotion2D.b.Grad;

            //許容範囲を算出
            Real delta = 0.00001f;

            Assert.AreEqual(cYdata.Length, y.Data.Length);
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);
            Assert.AreEqual(cWgrad.Length, convolution2D.Weight.Grad.Length);
            Assert.AreEqual(cbgrad.Length, convolution2D.Bias.Grad.Length);

            //y
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //x.grad
            for (int i = 0; i < x.Grad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }

            delta = 0.1f;
            //W.grad
            for (int i = 0; i < convolution2D.Weight.Grad.Length; i++)
            {
                Assert.AreEqual(cWgrad[i], convolution2D.Weight.Grad[i], delta);
            }

            //b.grad
            for (int i = 0; i < convolution2D.Bias.Grad.Length; i++)
            {
                Assert.AreEqual(cbgrad[i], convolution2D.Bias.Grad[i], delta);
            }
        }
Beispiel #22
0
        public void LRNRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int   n = Mother.Dice.Next(2, 7);
            float k = (float)Mother.Dice.NextDouble() * 3;

            int batchCount = Mother.Dice.Next(1, 5);
            int ch         = Mother.Dice.Next(1, 5);
            int width      = Mother.Dice.Next(1, 16);
            int height     = Mother.Dice.Next(1, 16);

            Real[,,,] input   = (Real[, , , ])Initializer.GetRealNdArray(new[] { batchCount, ch, height, width });
            Real[,,,] dummyGy = (Real[, , , ])Initializer.GetRealNdArray(new[] { batchCount, ch, height, width });


            //chainer
            NChainer.LocalResponseNormalization <Real> cLocalResponseNormalization = new NChainer.LocalResponseNormalization <Real>(n, k);

            Variable <Real> cX = new Variable <Real>(Real.ToBaseNdArray(input));

            Variable <Real> cY = cLocalResponseNormalization.Forward(cX);

            cY.Grad = Real.ToBaseNdArray(dummyGy);

            cY.Backward();


            //kelpnet
            KelpNet.LRN lrn = new LRN(n, k);

            NdArray x = new NdArray(Real.ToRealArray(input), new[] { ch, height, width }, batchCount);

            NdArray y = lrn.Forward(x)[0];

            y.Grad = Real.ToRealArray(dummyGy);

            y.Backward();


            Real[] cYdata = Real.ToRealArray((Real[, , , ])cY.Data);
            Real[] cXgrad = Real.ToRealArray((Real[, , , ])cX.Grad);

            //許容範囲を算出
            double delta = 0.00001;

            //y
            Assert.AreEqual(cYdata.Length, y.Data.Length);
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //x.grad
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);
            for (int i = 0; i < x.Grad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }
        }
Beispiel #23
0
        ////////////////////////////////////////////////////////////////////////////////////////////////////
        /// <summary>   Backward. </summary>
        ///
        /// <param name="ys">   A variable-length parameters list containing ys. </param>
        ///
        /// <seealso cref="M:KelpNet.Common.Functions.Function.Backward(params NdArray[])"/>
        ////////////////////////////////////////////////////////////////////////////////////////////////////

        public override void Backward(bool verbose = true, [NotNull] params NdArray[] ys)
        {
            NdArray.Backward(verbose, ys[0]);
        }
Beispiel #24
0
        public void RandomTest(bool gpuEnable)
        {
            Python.Initialize();
            Chainer.Initialize();

            int inputCount  = Mother.Dice.Next(1, 50);
            int outputCount = Mother.Dice.Next(1, 50);
            int batchCount  = Mother.Dice.Next(1, 5);

            Real[,] input = Initializer.GetRandomValues <Real[, ]>(batchCount, inputCount);

            Real[,] dummyGy = Initializer.GetRandomValues <Real[, ]>(batchCount, outputCount);
            Real[,] w       = Initializer.GetRandomValues <Real[, ]>(outputCount, inputCount);

            Real[] b = Initializer.GetRandomValues <Real[]>(outputCount);

            //Chainer
            NChainer.Linear <Real> cLinear = new NChainer.Linear <Real>(inputCount, outputCount, false, w, b);

            Variable <Real> cX = new Variable <Real>(input);

            Variable <Real> cY = cLinear.Forward(cX);

            cY.Grad = dummyGy;

            cY.Backward();


            //KelpNet
            CL.Linear <Real> linear = new CL.Linear <Real>(inputCount, outputCount, false, w, b, gpuEnable: gpuEnable);

            NdArray <Real> x = new NdArray <Real>(input, asBatch: true);

            NdArray <Real> y = linear.Forward(x)[0];

            y.Grad = dummyGy.Flatten();

            y.Backward();


            Real[] cYdata = ((Real[, ])cY.Data).Flatten();
            Real[] cXgrad = ((Real[, ])cX.Grad).Flatten();

            Real[] cWgrad = ((Real[, ])cLinear.W.Grad).Flatten();
            Real[] cbgrad = (Real[])cLinear.b.Grad;

            //許容範囲を算出
            Real delta = 0.00001f;

            //y
            Assert.AreEqual(cYdata.Length, y.Data.Length);
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //x.grad
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);
            for (int i = 0; i < x.Grad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }

            //W.grad
            Assert.AreEqual(cWgrad.Length, linear.Weight.Grad.Length);
            for (int i = 0; i < linear.Weight.Grad.Length; i++)
            {
                Assert.AreEqual(cWgrad[i], linear.Weight.Grad[i], delta);
            }

            //b.grad
            Assert.AreEqual(cbgrad.Length, linear.Bias.Grad.Length);
            for (int i = 0; i < linear.Bias.Grad.Length; i++)
            {
                Assert.AreEqual(cbgrad[i], linear.Bias.Grad[i], delta);
            }
        }
Beispiel #25
0
        public void RandomTest(bool gpuEnable)
        {
            Python.Initialize();
            Chainer.Initialize();

            int batchCount = Mother.Dice.Next(1, 5);
            int chCount    = Mother.Dice.Next(1, 5);
            int wideSize   = Mother.Dice.Next(8, 32);
            int heightSize = Mother.Dice.Next(8, 32);

            int kWidth  = Mother.Dice.Next(1, 5);
            int kHeight = Mother.Dice.Next(1, 5);

            int strideX = Mother.Dice.Next(1, 5);
            int strideY = Mother.Dice.Next(1, 5);

            int padX = Mother.Dice.Next(0, 5);
            int padY = Mother.Dice.Next(0, 5);

            bool coverAll = Mother.Dice.Next(1) == 0;

            int outputHeight = coverAll ?
                               (int)Math.Floor((heightSize - kHeight + padY * 2.0 + strideY - 1) / strideY) + 1 :
                               (int)Math.Floor((heightSize - kHeight + padY * 2.0) / strideY) + 1;

            int outputWidth = coverAll ?
                              (int)Math.Floor((wideSize - kWidth + padX * 2.0 + strideX - 1) / strideX) + 1 :
                              (int)Math.Floor((wideSize - kWidth + padX * 2.0) / strideX) + 1;

            Real[,,,] input = (Real[, , , ])Initializer.GetRealNdArray(new[] { batchCount, chCount, heightSize, wideSize });

            Real[,,,] dummyGy = (Real[, , , ])Initializer.GetRealNdArray(new[] { batchCount, chCount, outputHeight, outputWidth });

            //Chainer
            NChainer.MaxPooling2D <Real> cMaxPooling2D = new NChainer.MaxPooling2D <Real>(
                new[] { kHeight, kWidth },
                new[] { strideY, strideX },
                new[] { padY, padX }
                );

            Variable <Real> cX = new Variable <Real>(Real.ToBaseNdArray(input));

            Variable <Real> cY = cMaxPooling2D.Forward(cX);

            cY.Grad = Real.ToBaseNdArray(dummyGy);

            cY.Backward();


            //KelpNet
            KelpNet.CL.MaxPooling2D maxPooling2D = new KelpNet.CL.MaxPooling2D(
                new[] { kWidth, kHeight },
                new[] { strideX, strideY },
                new[] { padX, padY },
                gpuEnable: gpuEnable);

            NdArray x = new NdArray(Real.ToRealArray(input), new[] { chCount, heightSize, wideSize }, batchCount);

            NdArray y = maxPooling2D.Forward(x)[0];

            y.Grad = Real.ToRealArray(dummyGy);

            y.Backward();

            Real[] cYdata = Real.ToRealArray((Real[, , , ])cY.Data.Copy());
            Real[] cXgrad = Real.ToRealArray((Real[, , , ])cX.Grad.Copy());

            //許容範囲を算出
            double delta = 0.00001;

            Assert.AreEqual(cYdata.Length, y.Data.Length);
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);

            //y
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //x.grad
            for (int i = 0; i < x.Grad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }
        }
Beispiel #26
0
        public void RnnLSTMRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            Real[,] input = { { 1.0f }, { 3.0f }, { 5.0f }, { 7.0f }, { 9.0f } };
            Real[,] teach = { { 3.0f }, { 5.0f }, { 7.0f }, { 9.0f }, { 11.0f } };

            Real[,] input2 = { { 3.0f }, { 5.0f }, { 7.0f }, { 9.0f }, { 11.0f } };
            Real[,] teach2 = { { 5.0f }, { 7.0f }, { 9.0f }, { 11.0f }, { 13.0f } };

            int outputCount = 1;
            int inputCount  = 1;
            int hiddenCount = 2;

            Real[,] upwardInit      = Initializer.GetRandomValues <Real[, ]>(hiddenCount, hiddenCount);
            Real[,] lateralInit     = Initializer.GetRandomValues <Real[, ]>(hiddenCount, hiddenCount);
            Real[,,] biasInit       = Initializer.GetRandomValues <Real[, , ]>(1, hiddenCount, 1);
            Real[,,] forgetBiasInit = Initializer.GetRandomValues <Real[, , ]>(1, hiddenCount, 1);

            //Chainer
            Real[,] w1 = Initializer.GetRandomValues <Real[, ]>(hiddenCount, inputCount);
            Real[] b1 = Initializer.GetRandomValues <Real[]>(hiddenCount);

            //Chainer
            Linear <Real> cLinear1 = new Linear <Real>(inputCount, hiddenCount, false, w1, b1);

            NChainer.LSTM <Real> cLstm = new NChainer.LSTM <Real>(hiddenCount, hiddenCount, lateralInit, upwardInit, biasInit, forgetBiasInit);

            Real[,] w2 = Initializer.GetRandomValues <Real[, ]>(outputCount, hiddenCount);
            Real[]        b2       = Initializer.GetRandomValues <Real[]>(outputCount);
            Linear <Real> cLinear2 = new Linear <Real>(hiddenCount, outputCount, false, w2, b2);

            Variable <Real> cX1  = new Variable <Real>(input);
            Variable <Real> cY11 = cLinear1.Forward(cX1);
            Variable <Real> cY12 = cLstm.Forward(cY11);
            Variable <Real> cY13 = cLinear2.Forward(cY12);
            Variable <Real> cT   = new Variable <Real>(teach);

            Variable <Real> cLoss = new NChainer.MeanSquaredError <Real>().Forward(cY13, cT);

            cLoss.Backward();


            //KelpNet
            CL.Linear <Real> linear1 = new CL.Linear <Real>(inputCount, hiddenCount, false, w1, b1);
            LSTM <Real>      lstm    = new LSTM <Real>(hiddenCount, hiddenCount, lateralInit, upwardInit, biasInit, forgetBiasInit);

            CL.Linear <Real> linear2 = new CL.Linear <Real>(hiddenCount, outputCount, false, w2, b2);

            NdArray <Real> x1  = new NdArray <Real>(input, asBatch: true);
            NdArray <Real> y11 = linear1.Forward(x1)[0];
            NdArray <Real> y12 = lstm.Forward(y11)[0];
            NdArray <Real> y13 = linear2.Forward(y12)[0];
            NdArray <Real> t   = new NdArray <Real>(teach, asBatch: true);

            NdArray <Real> loss = new MeanSquaredError <Real>().Evaluate(y13, t);

            y13.Backward();

            Real[] cY11data = ((Real[, ])cY11.Data).Flatten();
            Real[] cY12data = ((Real[, ])cY12.Data).Flatten();
            Real[] cY13data = ((Real[, ])cY13.Data).Flatten();
            Real[] cXgrad   = ((Real[, ])cX1.Grad).Flatten();

            Real[] cupwardWGrad = ((Real[, ])cLstm.upward.W.Grad).Flatten();
            Real[] cupwardbGrad = (Real[])cLstm.upward.b.Grad;


            //許容範囲を設定
            Real delta = 0.00001f;

            //y11
            Assert.AreEqual(cY11data.Length, y11.Data.Length);
            for (int i = 0; i < cY11data.Length; i++)
            {
                Assert.AreEqual(cY11data[i], y11.Data[i], delta);
            }

            //y12
            Assert.AreEqual(cY12data.Length, y12.Data.Length);
            for (int i = 0; i < cY12data.Length; i++)
            {
                Assert.AreEqual(cY12data[i], y12.Data[i], delta);
            }

            //y13
            Assert.AreEqual(cY13data.Length, y13.Data.Length);
            for (int i = 0; i < cY13data.Length; i++)
            {
                Assert.AreEqual(cY13data[i], y13.Data[i], delta);
            }

            //許容範囲を設定
            delta = 0.0001f;

            //loss
            Assert.AreEqual(cLoss.Data[0], loss.Data[0], delta);

            //x.Grad
            Assert.AreEqual(cXgrad.Length, x1.Grad.Length);
            for (int i = 0; i < cXgrad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x1.Grad[i], delta);
            }

            Real[] cWgrad11 = ((Real[, ])cLinear1.W.Grad).Flatten();
            Real[] cbgrad11 = (Real[])cLinear1.b.Grad;

            //W.grad
            Assert.AreEqual(cWgrad11.Length, linear1.Weight.Grad.Length);
            for (int i = 0; i < linear1.Weight.Grad.Length; i++)
            {
                Assert.AreEqual(cWgrad11[i], linear1.Weight.Grad[i], delta);
            }

            //b.grad
            Assert.AreEqual(cbgrad11.Length, linear1.Bias.Grad.Length);
            for (int i = 0; i < linear1.Bias.Grad.Length; i++)
            {
                Assert.AreEqual(cbgrad11[i], linear1.Bias.Grad[i], delta);
            }


            Real[] cWgrad12 = ((Real[, ])cLinear2.W.Grad).Flatten();
            Real[] cbgrad12 = (Real[])cLinear2.b.Grad;


            //W.grad
            Assert.AreEqual(cWgrad12.Length, linear2.Weight.Grad.Length);
            for (int i = 0; i < linear2.Weight.Grad.Length; i++)
            {
                Assert.AreEqual(cWgrad12[i], linear2.Weight.Grad[i], delta);
            }

            //b.grad
            Assert.AreEqual(cbgrad12.Length, linear2.Bias.Grad.Length);
            for (int i = 0; i < linear2.Bias.Grad.Length; i++)
            {
                Assert.AreEqual(cbgrad12[i], linear2.Bias.Grad[i], delta);
            }

            //W.grad
            int wLen = lstm.upward.Weight.Grad.Length;

            Assert.AreEqual(cupwardWGrad.Length, lstm.upward.Weight.Grad.Length);
            for (int i = 0; i < wLen; i++)
            {
                Assert.AreEqual(cupwardWGrad[i + wLen * 0], lstm.upward.Weight.Grad[i], delta);
            }

            //b.grad
            int bLen = lstm.upward.Bias.Length;

            Assert.AreEqual(cupwardbGrad.Length, lstm.upward.Bias.Grad.Length);
            for (int i = 0; i < bLen; i++)
            {
                Assert.AreEqual(cupwardbGrad[i + wLen * 0], lstm.upward.Bias.Grad[i], delta);
            }


            //2周目
            Variable <Real> cX2  = new Variable <Real>(input2);
            Variable <Real> cY21 = cLinear1.Forward(cX2);
            Variable <Real> cY22 = cLstm.Forward(cY21);
            Variable <Real> cY23 = cLinear2.Forward(cY22);
            Variable <Real> cT2  = new Variable <Real>(teach2);

            Variable <Real> cLoss2 = new NChainer.MeanSquaredError <Real>().Forward(cY23, cT2);

            //KelpNet
            NdArray <Real> x2  = new NdArray <Real>(input2, asBatch: true);
            NdArray <Real> y21 = linear1.Forward(x2)[0];
            NdArray <Real> y22 = lstm.Forward(y21)[0];
            NdArray <Real> y23 = linear2.Forward(y22)[0];
            NdArray <Real> t2  = new NdArray <Real>(teach2, asBatch: true);

            NdArray <Real> loss2 = new MeanSquaredError <Real>().Evaluate(y23, t2);

            Assert.AreEqual(cLoss2.Data[0], loss2.Data[0], delta);

            //Backwardを実行
            cLoss2.Backward();
            y23.Backward();


            Real[] cYdata21 = ((Real[, ])cY21.Data).Flatten();
            Real[] cYdata22 = ((Real[, ])cY22.Data).Flatten();
            Real[] cYdata23 = ((Real[, ])cY23.Data).Flatten();
            Real[] cXgrad2  = ((Real[, ])cX2.Grad).Flatten();

            Real[] cupwardWGrad2 = ((Real[, ])cLstm.upward.W.Grad).Flatten();
            Real[] cupwardbGrad2 = (Real[])cLstm.upward.b.Grad;
            Real[] clateralWGrad = ((Real[, ])cLstm.lateral.W.Grad).Flatten();

            //y21
            Assert.AreEqual(cYdata21.Length, y21.Data.Length);
            for (int i = 0; i < cYdata21.Length; i++)
            {
                Assert.AreEqual(cYdata21[i], y21.Data[i], delta);
            }

            //y22
            Assert.AreEqual(cYdata22.Length, y22.Data.Length);
            for (int i = 0; i < cYdata22.Length; i++)
            {
                Assert.AreEqual(cYdata22[i], y22.Data[i], delta);
            }

            //y23
            Assert.AreEqual(cYdata23.Length, y23.Data.Length);
            for (int i = 0; i < cYdata23.Length; i++)
            {
                Assert.AreEqual(cYdata23[i], y23.Data[i], delta);
            }

            //x.Grad
            Assert.AreEqual(cXgrad2.Length, x2.Grad.Length);
            for (int i = 0; i < cXgrad2.Length; i++)
            {
                Assert.AreEqual(cXgrad2[i], x2.Grad[i], delta);
            }

            //経由が多くかなり誤差が大きい為
            delta = 1.0f;

            Real[] cWgrad22 = ((Real[, ])cLinear2.W.Grad).Flatten();
            Real[] cbgrad22 = (Real[])cLinear2.b.Grad;

            //W.grad
            Assert.AreEqual(cWgrad22.Length, linear2.Weight.Grad.Length);
            for (int i = 0; i < linear2.Weight.Grad.Length; i++)
            {
                Assert.AreEqual(cWgrad22[i], linear2.Weight.Grad[i], delta);
            }

            //b.grad
            Assert.AreEqual(cbgrad22.Length, linear2.Bias.Grad.Length);
            for (int i = 0; i < linear2.Bias.Grad.Length; i++)
            {
                Assert.AreEqual(cbgrad22[i], linear2.Bias.Grad[i], delta);
            }


            delta = 2.0f;

            //W.grad
            Assert.AreEqual(clateralWGrad.Length, lstm.lateral.Weight.Grad.Length);
            for (int i = 0; i < clateralWGrad.Length; i++)
            {
                Assert.AreEqual(clateralWGrad[i + wLen * 0], lstm.lateral.Weight.Grad[i], delta);
            }

            for (int i = 0; i < wLen; i++)
            {
                Assert.AreEqual(cupwardWGrad2[i + wLen * 0], lstm.upward.Weight.Grad[i], delta);
            }

            //b.grad
            for (int i = 0; i < bLen; i++)
            {
                Assert.AreEqual(cupwardbGrad2[i + wLen * 0], lstm.upward.Bias.Grad[i], delta);
            }


            delta = 20.0f;

            Real[] cWgrad21 = ((Real[, ])cLinear1.W.Grad).Flatten();
            Real[] cbgrad21 = (Real[])cLinear1.b.Grad;

            //W.grad
            Assert.AreEqual(cWgrad21.Length, linear1.Weight.Grad.Length);
            for (int i = 0; i < linear1.Weight.Grad.Length; i++)
            {
                Assert.AreEqual(cWgrad21[i], linear1.Weight.Grad[i], delta);
            }

            //b.grad
            Assert.AreEqual(cbgrad21.Length, linear1.Bias.Grad.Length);
            for (int i = 0; i < linear1.Bias.Grad.Length; i++)
            {
                Assert.AreEqual(cbgrad21[i], linear1.Bias.Grad[i], delta);
            }
        }
Beispiel #27
0
        public void SGDRandomTest()
        {
            Python.Initialize();
            Chainer.Initialize();

            int inputCount  = Mother.Dice.Next(2, 50);
            int outputCount = Mother.Dice.Next(2, 50);
            int batchCount  = Mother.Dice.Next(1, 5);

            Real[,] input = (Real[, ])Initializer.GetRealNdArray(new[] { batchCount, inputCount });

            Real[,] dummyGy = (Real[, ])Initializer.GetRealNdArray(new[] { batchCount, outputCount });
            Real[,] w       = (Real[, ])Initializer.GetRealNdArray(new[] { outputCount, inputCount });

            Real[] b = Initializer.GetRealArray(outputCount);

            //Chainer
            NChainer.Linear <Real> cLinear = new NChainer.Linear <Real>(inputCount, outputCount, false, Real.ToBaseNdArray(w), Real.ToBaseArray(b));
            NChainer.SGD <Real>    cSgd    = new NChainer.SGD <Real>();
            cSgd.Setup(cLinear);

            Variable <Real> cX = new Variable <Real>(Real.ToBaseNdArray(input));

            Variable <Real> cY = cLinear.Forward(cX);

            cY.Grad = Real.ToBaseNdArray(dummyGy);

            cY.Backward();

            cSgd.Update();

            //KelpNet
            KelpNet.Linear linear = new KelpNet.Linear(inputCount, outputCount, false, w, b);
            KelpNet.SGD    sgd    = new SGD();
            sgd.SetUp(linear);

            NdArray x = new NdArray(Real.ToRealArray(input), new[] { inputCount }, batchCount);

            NdArray y = linear.Forward(x)[0];

            y.Grad = Real.ToRealArray(dummyGy);

            y.Backward();

            sgd.Update();


            Real[] cW = Real.ToRealArray((Real[, ])cLinear.W.Data);
            Real[] cb = (Real[])cLinear.b.Data;

            //許容範囲を算出
            double delta = 0.00001;

            //W.grad
            Assert.AreEqual(cW.Length, linear.Weight.Data.Length);
            for (int i = 0; i < linear.Weight.Data.Length; i++)
            {
                Assert.AreEqual(cW[i], linear.Weight.Data[i], delta);
            }

            //b.grad
            Assert.AreEqual(cb.Length, linear.Bias.Data.Length);
            for (int i = 0; i < linear.Bias.Data.Length; i++)
            {
                Assert.AreEqual(cb[i], linear.Bias.Data[i], delta);
            }
        }
Beispiel #28
0
        public void TrainTest(bool isTtrain, bool finetune)
        {
            Python.Initialize();
            Chainer.Initialize();

            int batchCount = Mother.Dice.Next(1, 50);
            int ioCount    = Mother.Dice.Next(1, 50);

            Real[,] input = Initializer.GetRandomValues <Real[, ]>(batchCount, ioCount);

            Real[,] dummyGy = Initializer.GetRandomValues <Real[, ]>(batchCount, ioCount);

            Real[] gamma = Initializer.GetRandomValues <Real[]>(ioCount);
            Real[] beta  = Initializer.GetRandomValues <Real[]>(ioCount);

            Real[] avgMean = Initializer.GetRandomValues <Real[]>(ioCount);
            Real[] avgVar  = Initializer.GetRandomValues <Real[]>(ioCount);

            //Chainer
            Chainer.Config["train"] = isTtrain;

            NChainer.BatchNormalization <Real> cBatchNormalization = new NChainer.BatchNormalization <Real>(ioCount, dtype: typeof(Real));

            cBatchNormalization.gamma = new Variable <Real>(gamma);
            cBatchNormalization.beta  = new Variable <Real>(beta);

            cBatchNormalization.avgMean = avgMean;
            cBatchNormalization.avgVar  = avgVar;

            Variable <Real> cX = new Variable <Real>(input);

            Variable <Real> cY = cBatchNormalization.Forward(cX, finetune);

            cY.Grad = dummyGy;

            cY.Backward();

            //KelpNet
            KelpNet.BatchNormalization <Real> batchNormalization = new BatchNormalization <Real>(ioCount, train: isTtrain, finetune: finetune);

            batchNormalization.Gamma.Data = gamma;
            batchNormalization.Beta.Data  = beta;

            batchNormalization.AvgMean.Data = avgMean;
            batchNormalization.AvgVar.Data  = avgVar;

            NdArray <Real> x = new NdArray <Real>(input, asBatch: true);

            NdArray <Real> y = batchNormalization.Forward(x)[0];

            y.Grad = dummyGy.Flatten();

            y.Backward();


            Real[] cYdata = ((Real[, ])cY.Data).Flatten();
            Real[] cXgrad = ((Real[, ])cX.Grad).Flatten();

            Real[] cGammaGrad = (Real[])cBatchNormalization.gamma.Grad;
            Real[] cBetaGrad  = (Real[])cBatchNormalization.beta.Grad;

            //許容範囲を算出
            Real delta = 0.00005f;

            //y
            Assert.AreEqual(cYdata.Length, y.Data.Length);
            for (int i = 0; i < y.Data.Length; i++)
            {
                Assert.AreEqual(cYdata[i], y.Data[i], delta);
            }

            //x.grad
            Assert.AreEqual(cXgrad.Length, x.Grad.Length);
            for (int i = 0; i < x.Grad.Length; i++)
            {
                Assert.AreEqual(cXgrad[i], x.Grad[i], delta);
            }

            //gamma.grad
            Assert.AreEqual(cGammaGrad.Length, batchNormalization.Gamma.Grad.Length);
            for (int i = 0; i < batchNormalization.Gamma.Grad.Length; i++)
            {
                Assert.AreEqual(cGammaGrad[i], batchNormalization.Gamma.Grad[i], delta);
            }

            //beta.grad
            Assert.AreEqual(cBetaGrad.Length, batchNormalization.Beta.Grad.Length);
            for (int i = 0; i < batchNormalization.Beta.Grad.Length; i++)
            {
                Assert.AreEqual(cBetaGrad[i], batchNormalization.Beta.Grad[i], delta);
            }
        }