Centralize várias saídas na camada de saída do diagrama tikz da rede neural

Centralize várias saídas na camada de saída do diagrama tikz da rede neural

Esta questão está construindo uma solução postadaaqui. O código abaixo deve ser otimizado, pois a camada de saída não está centralizada no resto da figura.

Gostaria de saber como centralizar a camada de saída com o restante da figura.

Além disso, eu queria saber como definir a posição correta da camada de saída em vez de codificá-la da maneira que a possui atualmente:

\node[output neuron, pin=right:Output \#\y] (O-\name) at (4*\layersep,-\y) {};

insira a descrição da imagem aqui

Aqui está o código que tenho até agora:

\documentclass{article}
\usepackage{tikz}

\begin{document}
\pagestyle{empty}

\def\layersep{2.5cm}

\begin{tikzpicture}[
   shorten >=1pt,->,
   draw=black!50,
    node distance=\layersep,
    every pin edge/.style={<-,shorten <=1pt},
    neuron/.style={circle,fill=black!25,minimum size=17pt,inner sep=0pt},
    input neuron/.style={neuron, fill=green!50},
    output neuron/.style={neuron, fill=red!50},
    hidden neuron/.style={neuron, fill=blue!50},
    annot/.style={text width=4em, text centered}
]

% Draw the input layer nodes
\foreach \name / \y in {1,...,8}
% This is the same as writing \foreach \name / \y in {1/1,2/2,3/3,4/4}
    \node[input neuron, pin=left:Input \#\y] (I-\name) at (0,-\y) {};

% set number of hidden layers
\newcommand\Nhidden{3}

% Draw the hidden layer nodes
\foreach \N in {1,...,\Nhidden} {
   \foreach \y in {1,...,9} {
      \path[yshift=0.5cm]
          node[hidden neuron] (H\N-\y) at (\N*\layersep,-\y cm) {};
       }
\node[annot,above of=H\N-1, node distance=1cm] (hl\N) {Hidden layer \N};
}

% Draw the output layer node
\foreach \name / \y in {1,...,4}
% This is the same as writing \foreach \name / \y in {1/1,2/2,3/3,4/4}
    \node[output neuron, pin=right:Output \#\y] (O-\name) at (4*\layersep,-\y) {};
    %  How to calculate the exact location of the output layers instead of hardcoding the value

% Connect every node in the input layer with every node in the
% hidden layer.
\foreach \source in {1,...,8}
    \foreach \dest in {1,...,9}
        \path (I-\source) edge (H1-\dest);

% connect all hidden stuff
\foreach [remember=\N as \lastN (initially 1)] \N in {2,...,\Nhidden}
   \foreach \source in {1,...,9}
       \foreach \dest in {1,...,9}
           \path (H\lastN-\source) edge (H\N-\dest);

% Connect every node in the hidden layer with the output layer
\foreach [remember=\N as \lastN (initially 3)] \N in {2,...,\Nhidden}
\foreach \source in {1,...,9}
    \foreach \dest in {1,...,4}
        \path (H\lastN-\source) edge (O-\dest);

% Annotate the layers

\node[annot,left of=hl1] {Input layer};
\node[annot,right of=hl\Nhidden] {Output layer};
\end{tikzpicture}
% End of code
\end{document} 

Responder1

Altere as coordenadas dos nós na camada de saída de (4*\layersep,-\y)para (4*\layersep,-\y-2):

insira a descrição da imagem aqui

MWE completo:

\documentclass[tikz, margin=3mm]{standalone}

\begin{document}
\def\layersep{2.5cm}

\begin{tikzpicture}[
   shorten >=1pt,->,
   draw=black!50,
    node distance=\layersep,
    every pin edge/.style={<-,shorten <=1pt},
    neuron/.style={circle,fill=black!25,minimum size=17pt,inner sep=0pt},
    input neuron/.style={neuron, fill=green!50},
    output neuron/.style={neuron, fill=red!50},
    hidden neuron/.style={neuron, fill=blue!50},
    annot/.style={text width=4em, text centered}
]

% Draw the input layer nodes
\foreach \name / \y in {1,...,8}
% This is the same as writing \foreach \name / \y in {1/1,2/2,3/3,4/4}
    \node[input neuron, pin=left:Input \#\y] (I-\name) at (0,-\y) {};

% set number of hidden layers
\newcommand\Nhidden{3}

% Draw the hidden layer nodes
\foreach \N in {1,...,\Nhidden} {
   \foreach \y in {1,...,9} {
      \path[yshift=0.5cm]
          node[hidden neuron] (H\N-\y) at (\N*\layersep,-\y cm) {};
       }
\node[annot,above of=H\N-1, node distance=1cm] (hl\N) {Hidden layer \N};
}

% Draw the output layer node
\foreach \name / \y in {1,...,4}
% This is the same as writing \foreach \name / \y in {1/1,2/2,3/3,4/4}
    \node[output neuron, 
          pin=right:Output \#\y] (O-\name) 
          at (4*\layersep,-\y-2) {};  % <-----------
    %  How to calculate the exact location of the output layers instead of hardcoding the value

% Connect every node in the input layer with every node in the
% hidden layer.
\foreach \source in {1,...,8}
    \foreach \dest in {1,...,9}
        \path (I-\source) edge (H1-\dest);

% connect all hidden stuff
\foreach [remember=\N as \lastN (initially 1)] \N in {2,...,\Nhidden}
   \foreach \source in {1,...,9}
       \foreach \dest in {1,...,9}
           \path (H\lastN-\source) edge (H\N-\dest);

% Connect every node in the hidden layer with the output layer
\foreach [remember=\N as \lastN (initially 3)] \N in {2,...,\Nhidden}
\foreach \source in {1,...,9}
    \foreach \dest in {1,...,4}
        \path (H\lastN-\source) edge (O-\dest);

% Annotate the layers

\node[annot,left of=hl1] {Input layer};
\node[annot,right of=hl\Nhidden] {Output layer};
\end{tikzpicture}
\end{document}

Responder2

É difícil fornecer uma resposta não codificada, pois todos os outros valores são codificados. Você precisa

at (4*\layersep,{-\y*1cm-(9-4-1)*0.5cm})

porque existem 9 nós ocultos por camada, 4 nós de saída, e então há um código rígido [yshift=0.5cm]na construção dos neurônios ocultos, portanto o adicional -1. O resultado é que se você alterar o número de nós de saída para 4outro valor, será necessário alterar na 4fórmula acima para o mesmo valor.

\documentclass{article}

\usepackage{tikz}
\begin{document}
\pagestyle{empty}

\def\layersep{2.5cm}

\begin{tikzpicture}[
   shorten >=1pt,->,
   draw=black!50,
    node distance=\layersep,
    every pin edge/.style={<-,shorten <=1pt},
    neuron/.style={circle,fill=black!25,minimum size=17pt,inner sep=0pt},
    input neuron/.style={neuron, fill=green!50},
    output neuron/.style={neuron, fill=red!50},
    hidden neuron/.style={neuron, fill=blue!50},
    annot/.style={text width=4em, text centered}
]

% Draw the input layer nodes
\foreach \name / \y in {1,...,8}
% This is the same as writing \foreach \name / \y in {1/1,2/2,3/3,4/4}
    \node[input neuron, pin=left:Input \#\y] (I-\name) at (0,-\y) {};

% set number of hidden layers
\newcommand\Nhidden{3}

% Draw the hidden layer nodes
\foreach \N in {1,...,\Nhidden} {
   \foreach \y in {1,...,9} {
      \path[yshift=0.5cm]
          node[hidden neuron] (H\N-\y) at (\N*\layersep,-\y*1cm) {};
       }
\node[annot,above of=H\N-1, node distance=1cm] (hl\N) {Hidden layer \N};
}

% Draw the output layer node
\foreach \name / \y in {1,...,4}
% This is the same as writing \foreach \name / \y in {1/1,2/2,3/3,4/4}
    \node[output neuron, pin=right:Output \#\y] (O-\name) 
    at (4*\layersep,{-\y*1cm-(9-4-1)*0.5cm}) {};
    %  How to calculate the exact location of the output layers instead of hardcoding the value

% Connect every node in the input layer with every node in the
% hidden layer.
\foreach \source in {1,...,8}
    \foreach \dest in {1,...,9}
        \path (I-\source) edge (H1-\dest);

% connect all hidden stuff
\foreach [remember=\N as \lastN (initially 1)] \N in {2,...,\Nhidden}
   \foreach \source in {1,...,9}
       \foreach \dest in {1,...,9}
           \path (H\lastN-\source) edge (H\N-\dest);

% Connect every node in the hidden layer with the output layer
\foreach [remember=\N as \lastN (initially 3)] \N in {2,...,\Nhidden}
\foreach \source in {1,...,9}
    \foreach \dest in {1,...,4}
        \path (H\lastN-\source) edge (O-\dest);

% Annotate the layers

\node[annot,left of=hl1] {Input layer};
\node[annot,right of=hl\Nhidden] {Output layer};
\end{tikzpicture}
\end{document}

insira a descrição da imagem aqui

informação relacionada