public static Tensor <float> Conv(string name, Tensor <float> x, Array <float> kernel, Block pooling = null, bool bias = true) { var einstein = "i,io->o"; if (x.NDim == 3) { einstein = "bi,io->bo"; } var W = Op.Shared(kernel, name); W.Tag(KERNEL); W.Tag(name); var y = Op.ConvolveCustom(x, W, einstein); if (pooling != null) { y = pooling(y); } if (bias) { var b_shape = new int[y.NDim]; for (int i = 0; i < y.NDim - 1; ++i) { b_shape[i] = 1; } b_shape[y.NDim - 1] = kernel.Shape[kernel.NDim - 1]; var b = Op.Shared(NN.Zeros(b_shape), name + "_bias"); //var b = Op.Shared(NN.Random.Uniform(-s, s, b_shape), name + "_bias"); b.Tag(BIAS); b.Tag(name); y += b; } y.Name = name + "_out"; return(y); }