1from chainer import backend 2from chainer import function_node 3from chainer import utils 4from chainer.utils import type_check 5 6 7class Arctanh(function_node.FunctionNode): 8 9 """Elementwise inverse hyperbolic tangent function.""" 10 11 def check_type_forward(self, in_types): 12 type_check._argname(in_types, ('x',)) 13 x_type, = in_types 14 15 type_check.expect(x_type.dtype.kind == 'f') 16 17 def forward(self, inputs): 18 self.retain_inputs((0,)) 19 x, = inputs 20 xp = backend.get_array_module(x) 21 y = xp.arctanh(x) 22 return utils.force_array(y, dtype=x.dtype), 23 24 def backward(self, indexes, grad_outputs): 25 x, = self.get_retained_inputs() 26 gy, = grad_outputs 27 gx = 1. / (1 - x ** 2) * gy 28 return gx, 29 30 31def arctanh(x): 32 """Elementwise inverse hyperbolic tangent function. 33 34 Args: 35 x (:class:`~chainer.Variable` or :ref:`ndarray`): Input variable. 36 37 Returns: 38 ~chainer.Variable: Output variable. 39 40 """ 41 return Arctanh().apply((x,))[0] 42