/// <summary> /// 增加首个卷积层 /// </summary> /// <param name="cnnConvolutionLayer"></param> public void AddCnnConvolutionLayer(int convolutionKernelCount, int inputWidth, int inputHeight, int receptiveFieldWidth, int receptiveFieldHeight, int offsetWidth, int offsetHeight, CnnNode.ActivationFunctionTypes activationFunctionType, int poolingReceptiveFieldWidth, int poolingReceptiveFieldHeight, CnnPooling.PoolingTypes poolingType, bool standardization) { CnnConvolutionLayer cnnConvolutionLayer = new CnnConvolutionLayer(); //创建卷积层 cnnConvolutionLayer.CreateCnnKernel(convolutionKernelCount, inputWidth, inputHeight, receptiveFieldWidth, receptiveFieldHeight, offsetWidth, offsetHeight, activationFunctionType, 1, standardization, null); if (poolingType != 0) { //创建池化层 cnnConvolutionLayer.CreateCnnPooling(poolingReceptiveFieldWidth, poolingReceptiveFieldHeight, activationFunctionType, poolingType); } CnnConvolutionLayerList.Add(cnnConvolutionLayer); }
/// <summary> /// 增加后续卷积层 /// </summary> /// <param name="cnnConvolutionLayer"></param> public void AddCnnConvolutionLayer(int convolutionKernelCount, int receptiveFieldWidth, int receptiveFieldHeight, int offsetWidth, int offsetHeight, CnnNode.ActivationFunctionTypes activationFunctionType, int poolingReceptiveFieldWidth, int poolingReceptiveFieldHeight, CnnPooling.PoolingTypes poolingType, bool standardization, bool isFullLayerLinks) { var cnnConvolutionLayerLast = CnnConvolutionLayerList[CnnConvolutionLayerList.Count - 1];//最后的卷积层 bool[,] layerLinks = new bool[convolutionKernelCount, cnnConvolutionLayerLast.ConvolutionKernelCount]; if (!isFullLayerLinks) { //随机创建卷积层间连接 Random random = new Random(); for (int i = 0; i < convolutionKernelCount; i++) { int linkCount = 0; //每层链接数 while (linkCount < 2) //确保最低链接数 { for (int j = 0; j < cnnConvolutionLayerLast.ConvolutionKernelCount; j++) { if (random.NextDouble() < 0.5) { layerLinks[i, j] = false; } else { layerLinks[i, j] = true; linkCount++; } } } //排除相同链接 for (int j = 0; j < i; j++) { linkCount = 0;//相同链接数 for (int k = 0; k < cnnConvolutionLayerLast.ConvolutionKernelCount; k++) { if (layerLinks[i, k] == layerLinks[j, k]) { linkCount++; } } if (linkCount == cnnConvolutionLayerLast.ConvolutionKernelCount) { i--; break; } } } } else { //全链接 for (int i = 0; i < convolutionKernelCount; i++) { for (int j = 0; j < cnnConvolutionLayerLast.ConvolutionKernelCount; j++) { layerLinks[i, j] = true; } } } convolutionLinkList.Add(layerLinks); CnnConvolutionLayer cnnConvolutionLayer = new CnnConvolutionLayer(); //创建卷积层 cnnConvolutionLayer.CreateCnnKernel(convolutionKernelCount, cnnConvolutionLayerLast.OutputWidth, cnnConvolutionLayerLast.OutputHeight, receptiveFieldWidth, receptiveFieldHeight, offsetWidth, offsetHeight, activationFunctionType, cnnConvolutionLayerLast.ConvolutionKernelCount, standardization, layerLinks); if (poolingType != 0) { //创建池化层 cnnConvolutionLayer.CreateCnnPooling(poolingReceptiveFieldWidth, poolingReceptiveFieldHeight, activationFunctionType, poolingType); } CnnConvolutionLayerList.Add(cnnConvolutionLayer); }