def test_newton_order_one(self, dtype):
        jacobian_mat = tf.constant([[-1.]], dtype=dtype)
        real_dtype = abs(jacobian_mat).dtype
        bdf_coefficient = tf.constant(-0.1850, dtype=dtype)
        first_order_newton_coefficient = 1. / (1. - bdf_coefficient)
        step_size = tf.constant(0.01, dtype=real_dtype)
        unitary, upper = bdf_util.newton_qr(jacobian_mat,
                                            first_order_newton_coefficient,
                                            step_size)

        backward_differences = tf.constant(
            [[1.], [-1.], [0.], [0.], [0.], [0.]], dtype=dtype)
        ode_fn_vec = lambda time, state: -state
        order = tf.constant(1, dtype=tf.int32)
        time = tf.constant(0., dtype=real_dtype)
        tol = tf.constant(1e-6, dtype=real_dtype)

        # The equation we are trying to solve with Newton's method is linear.
        # Therefore, we should observe exact convergence after one iteration. An
        # additional iteration is required to obtain an accurate error estimate,
        # making the total number of iterations 2.
        max_num_newton_iters = 2

        converged, next_backward_difference, next_state, _ = bdf_util.newton(
            backward_differences, max_num_newton_iters,
            first_order_newton_coefficient, ode_fn_vec, order, step_size, time,
            tol, unitary, upper)
        self.assertEqual(self.evaluate(converged), True)

        state = backward_differences[0, :]
        step_size_cast = tf.cast(step_size, dtype=dtype)
        exact_next_state = (
            (1. - bdf_coefficient) * state +
            bdf_coefficient) / (1. + step_size_cast - bdf_coefficient)

        self.assertAllClose(self.evaluate(next_backward_difference),
                            self.evaluate(exact_next_state))
        self.assertAllClose(self.evaluate(next_state),
                            self.evaluate(exact_next_state))
Example #2
0
 def update_factorization():
     return bdf_util.newton_qr(
         jacobian_mat, newton_coefficients_array.read(order),
         step_size)