<commit_before># Copyright 2014-2017 The ODL contributors
#
# This file is part of ODL.
#
# This Source Code Form is subject to the terms of the Mozilla Public License,
# v. 2.0. If a copy of the MPL was not distributed with this file, You can
# obtain one at https://mozilla.org/MPL/2.0/.

"""Alternating dual (AD) upgrade algorithm studied by McGaffin and Fessler.

The alternating dual upgrade method is reported to be a flexible method which
allows an acceleration by permitting efficient calculations on a graphics card.
"""

from __future__ import print_function, division, absolute_import

import numpy as np

__all__ = ('adupdates',)


def adupdates(funcs, ops, x, stepsize, majs, niter, random=False,
              callback=None, callback_loop='outer'):
    """Alternating Dual updates method.

    The Alternating Dual (AD) updates method of McGaffin and Fessler is
    designed to solve an optimization problem of the form

        min_x sum_i f_i(L_i x)

    where ``f_i`` are proper, convex and lower semicontinuous functions and
    ``L_i`` are linear `Operator`s

    Parameters
    ----------
    funcs : sequence of `Functional`s
        All functions need to provide a `convex_conj` with a
        `proximal` factory.
    ops : sequence of `Operator`s
        Needs to provide as many elements as `funcs`.
    x : `LinearSpaceElement`
        Initial point, updated in-place.
    stepsize : positive float
        The stepsize for the outer (proximal point) iteration.
    majs : sequence of majorizers
        See the Notes section for details.
    niter : int
        Number of (outer) iterations.
    random : bool, optional
        If `True`, the order of the dual upgdates is chosen arbitrarily,
        otherwise the order provided by the lists `funcs`, `ops` and `majs`
        is used.
    callback : callable, optional
        Function called with the current iterate after each iteration.
    callback_loop : string, optional
       If 'inner', the `callback` function is called after each inner
       iteration, i.e., after each dual update. If 'outer', the `callback`
       function is called after each outer iteration, i.e., after each primal
       update.

    Notes
    -----
    The algorithm as implemented here is described in the article [MF2015],
    where it is applied to a tomography problem. It solves the problem

    .. math::
        \min_x \sum_{i=1}^m f_i(L_i x),

    where :math:`f_i` are proper, convex and lower semicontinuous functions<commit_msg>DOC: Minor improvements in adupdates docstring.<commit_after># Copyright 2014-2017 The ODL contributors
#
# This file is part of ODL.
#
# This Source Code Form is subject to the terms of the Mozilla Public License,
# v. 2.0. If a copy of the MPL was not distributed with this file, You can
# obtain one at https://mozilla.org/MPL/2.0/.

"""Alternating dual (AD) upgrade algorithm studied by McGaffin and Fessler.

The alternating dual upgrade method is reported to be a flexible method which
allows an acceleration by permitting efficient calculations on a graphics card.
"""

from __future__ import print_function, division, absolute_import

import numpy as np

__all__ = ('adupdates',)


def adupdates(funcs, ops, x, stepsize, majs, niter, random=False,
              callback=None, callback_loop='outer'):
    """Alternating Dual updates method.

    The Alternating Dual (AD) updates method of McGaffin and Fessler is
    designed to solve an optimization problem of the form

        min_x sum_i f_i(L_i x)

    where ``f_i`` are proper, convex and lower semicontinuous functions and
    ``L_i`` are linear `Operator`s.

    Parameters
    ----------
    funcs : sequence of `Functional`s
        All functions need to provide a `convex_conj` with a
        `proximal` factory.
    ops : sequence of `Operator`s
        Needs to provide as many elements as `funcs`.
    x : `LinearSpaceElement`
        Initial point, updated in-place.
    stepsize : positive float
        The stepsize for the outer (proximal point) iteration.
    majs : sequence of majorizers
        See the Notes section for details.
    niter : int
        Number of (outer) iterations.
    random : bool, optional
        If `True`, the order of the dual upgdates is chosen randomly,
        otherwise the order provided by the lists `funcs`, `ops` and `majs`
        is used.
    callback : callable, optional
        Function called with the current iterate after each iteration.
    callback_loop : {'inner', 'outer'}, optional
       If 'inner', the `callback` function is called after each inner
       iteration, i.e., after each dual update. If 'outer', the `callback`
       function is called after each outer iteration, i.e., after each primal
       update.

    Notes
    -----
    The algorithm as implemented here is described in the article [MF2015],
    where it is applied to a tomography problem. It solves the problem

    .. math::
        \min_x \sum_{i=1}^m f_i(L_i x),

    where :math:`f_i` are proper, convex and lower semicontinuous functions
{'fraction_non_alphanumeric': 0.07524752475247524, 'fraction_numerical': 0.006732673267326733, 'mean_word_length': 2.949179046129789, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 2, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5544768', 'n_tokens_mistral': 1433, 'n_tokens_neox': 1352, 'n_words': 639}