from torch import nn


class DuelingQNetwork(nn.Module):
    """Dueling Q-network (https://arxiv.org/abs/1511.06581)"""

    def __init__(self, state_size, action_size, hidsize1=16, hidsize2=16):
        super(DuelingQNetwork, self).__init__()

        # value network
        self.value_network = nn.Sequential(
            nn.Linear(state_size, hidsize1),
            nn.ReLU(),
            nn.Linear(hidsize1, hidsize2),
            nn.ReLU(),
            nn.Linear(hidsize2, 1, bias=False),
        )

        # advantage network
        self.adv_network = nn.Sequential(
            nn.Linear(state_size, hidsize1),
            nn.ReLU(),
            nn.Linear(hidsize1, hidsize2),
            nn.ReLU(),
            nn.Linear(hidsize2, action_size, bias=False),
        )

    def forward(self, x):
        val = self.value_network(x)
        adv = self.adv_network(x)
        return val + adv - adv.mean()

from torch import nn


class DuelingQNetwork(nn.Module):
    """Dueling Q-network (https://arxiv.org/abs/1511.06581)"""

    def __init__(self, state_size, action_size, hidsize1=16, hidsize2=16):
        super(DuelingQNetwork, self).__init__()

        # value network
        self.value_network = nn.Sequential(
            nn.Linear(state_size, hidsize1),
            nn.ReLU(),
            nn.Linear(hidsize1, hidsize2),
            nn.ReLU(),
            nn.Linear(hidsize2, 1, bias=False),
        )

        # advantage network
        self.adv_network = nn.Sequential(
            nn.Linear(state_size, hidsize1),
            nn.ReLU(),
            nn.Linear(hidsize1, hidsize2),
            nn.ReLU(),
            nn.Linear(hidsize2, action_size, bias=False),
        )

    def forward(self, x):
        val = self.value_network(x)
        adv = self.adv_network(x)
        return val + adv - adv.mean()

Dueling Q-network (https://arxiv.org/abs/1511.06581) # value network # advantage network