Ejemplo n.º 1
0
def inference_ad3_local(unary_potentials,
                        pairwise_potentials,
                        edges,
                        relaxed=False,
                        verbose=0,
                        return_energy=False,
                        branch_and_bound=False,
                        inference_exception=None,
                        return_marginals=False):

    b_multi_type = isinstance(unary_potentials, list)
    if b_multi_type:
        res = ad3.general_graph(unary_potentials,
                                edges,
                                pairwise_potentials,
                                verbose=verbose,
                                n_iterations=4000,
                                exact=branch_and_bound)
    else:
        n_states, pairwise_potentials = \
            _validate_params(unary_potentials, pairwise_potentials, edges)
        unaries = unary_potentials.reshape(-1, n_states)
        res = ad3.general_graph(unaries,
                                edges,
                                pairwise_potentials,
                                verbose=verbose,
                                n_iterations=4000,
                                exact=branch_and_bound)

    unary_marginals, pairwise_marginals, energy, solver_status = res
    if verbose:
        print(solver_status)

    if solver_status in ["fractional", "unsolved"] and relaxed:
        if b_multi_type:
            y = (unary_marginals, pairwise_marginals)
        else:
            unary_marginals = unary_marginals.reshape(unary_potentials.shape)
            y = (unary_marginals, pairwise_marginals)
    else:
        if b_multi_type:
            if inference_exception and solver_status in [
                    "fractional", "unsolved"
            ]:
                raise InferenceException(solver_status)
            ly = list()
            _cum_n_states = 0
            for unary_marg in unary_marginals:
                ly.append(_cum_n_states + np.argmax(unary_marg, axis=-1))
                _cum_n_states += unary_marg.shape[1]
            y = np.hstack(ly)
        else:
            y = np.argmax(unary_marginals, axis=-1)
    if return_energy:
        return y, -energy
    if return_marginals:
        return y, unary_marginals
    return y
Ejemplo n.º 2
0
def inference_ad3(unary_potentials, pairwise_potentials, edges, relaxed=False,
                  verbose=0, return_energy=False, branch_and_bound=False):
    """Inference with AD3 dual decomposition subgradient solver.

    Parameters
    ----------
    unary_potentials : nd-array, shape (n_nodes, n_nodes)
        Unary potentials of energy function.

    pairwise_potentials : nd-array, shape (n_states, n_states) or (n_states, n_states, n_edges).
        Pairwise potentials of energy function.
        If the first case, edge potentials are assumed to be the same for all edges.
        In the second case, the sequence needs to correspond to the edges.

    edges : nd-array, shape (n_edges, 2)
        Graph edges for pairwise potentials, given as pair of node indices. As
        pairwise potentials are not assumed to be symmetric, the direction of
        the edge matters.

    relaxed : bool (default=False)
        Whether to return the relaxed solution (``True``) or round to the next
        integer solution (``False``).

    verbose : int (default=0)
        Degree of verbosity for solver.

    return_energy : bool (default=False)
        Additionally return the energy of the returned solution (according to
        the solver).  If relaxed=False, this is the energy of the relaxed, not
        the rounded solution.

    branch_and_bound : bool (default=False)
        Whether to attempt to produce an integral solution using
        branch-and-bound.

    Returns
    -------
    labels : nd-array
        Approximate (usually) MAP variable assignment.
        If relaxed=False, this is a tuple of unary and edge 'marginals'.
    """
    import ad3
    n_states, pairwise_potentials = \
        _validate_params(unary_potentials, pairwise_potentials, edges)

    unaries = unary_potentials.reshape(-1, n_states)
    res = ad3.general_graph(unaries, edges, pairwise_potentials, verbose=verbose,
                            n_iterations=4000, exact=branch_and_bound)
    unary_marginals, pairwise_marginals, energy, solver_status = res
    if verbose:
        print solver_status[0],

    if solver_status in ["fractional", "unsolved"] and relaxed:
        unary_marginals = unary_marginals.reshape(unary_potentials.shape)
        y = (unary_marginals, pairwise_marginals)
    else:
        y = np.argmax(unary_marginals, axis=-1)
    if return_energy:
        return y, -energy
    return y
Ejemplo n.º 3
0
def inference_ad3(unary_potentials, pairwise_potentials, edges, relaxed=False,
                  verbose=0, return_energy=False, branch_and_bound=False):
    """Inference with AD3 dual decomposition subgradient solver.

    Parameters
    ----------
    unary_potentials : nd-array, shape (n_nodes, n_nodes)
        Unary potentials of energy function.

    pairwise_potentials : nd-array, shape (n_states, n_states) or (n_states, n_states, n_edges).
        Pairwise potentials of energy function.
        If the first case, edge potentials are assumed to be the same for all edges.
        In the second case, the sequence needs to correspond to the edges.

    edges : nd-array, shape (n_edges, 2)
        Graph edges for pairwise potentials, given as pair of node indices. As
        pairwise potentials are not assumed to be symmetric, the direction of
        the edge matters.

    relaxed : bool (default=False)
        Whether to return the relaxed solution (``True``) or round to the next
        integer solution (``False``).

    verbose : int (default=0)
        Degree of verbosity for solver.

    return_energy : bool (default=False)
        Additionally return the energy of the returned solution (according to
        the solver).  If relaxed=False, this is the energy of the relaxed, not
        the rounded solution.

    branch_and_bound : bool (default=False)
        Whether to attempt to produce an integral solution using
        branch-and-bound.

    Returns
    -------
    labels : nd-array
        Approximate (usually) MAP variable assignment.
        If relaxed=False, this is a tuple of unary and edge 'marginals'.
    """
    import ad3
    n_states, pairwise_potentials = \
        _validate_params(unary_potentials, pairwise_potentials, edges)

    unaries = unary_potentials.reshape(-1, n_states)
    res = ad3.general_graph(unaries, edges, pairwise_potentials, verbose=verbose,
                            n_iterations=4000, exact=branch_and_bound)
    unary_marginals, pairwise_marginals, energy, solver_status = res
    if verbose:
        print(solver_status[0])

    if solver_status in ["fractional", "unsolved"] and relaxed:
        unary_marginals = unary_marginals.reshape(unary_potentials.shape)
        y = (unary_marginals, pairwise_marginals)
    else:
        y = np.argmax(unary_marginals, axis=-1)
    if return_energy:
        return y, -energy
    return y
Ejemplo n.º 4
0
def test_general_graph():
    unaries = np.array([[10, 11, 0], [1000, 1100, 1200]], dtype=np.float64)
    edges = np.array([[0, 1]])
    edge_weights = np.array([[[.00, .01, .02], [.10, .11, .12], [0, 0, 0]]],
                            dtype=np.float64)
    ret = general_graph(unaries, edges, edge_weights, verbose=1, exact=False)
    marginals, edge_marginals, value, solver_status = ret
    assert (marginals == np.array([[0., 1., 0.], [0., 0., 1.]])).all()
    assert (edge_marginals == np.array([[0, 0, 0, 0, 0, 1, 0, 0, 0]])).all()
    assert solver_status == 'integral'
Ejemplo n.º 5
0
def test_general_graph():
    unaries = np.array([[10, 11, 0 ],
                        [ 1000, 1100, 1200]], dtype=np.float64)
    edges = np.array([[0, 1]])
    edge_weights = np.array([[[.00, .01, .02],
                              [.10, .11, .12],
                              [0, 0, 0]]], dtype=np.float64)
    ret = general_graph(unaries, edges, edge_weights, verbose=1, exact=False)
    marginals, edge_marginals, value, solver_status = ret
    assert (marginals == np.array([[ 0.,  1.,  0.],
                                   [ 0.,  0.,  1.]])).all()
    assert (edge_marginals == np.array([[0, 0, 0, 0, 0, 1, 0, 0, 0]])).all()
    assert solver_status == 'integral'
Ejemplo n.º 6
0
def example_binary(plot=True):
    # generate trivial data
    x = np.ones((10, 10))
    x[:, 5:] = -1
    x_noisy = x + np.random.normal(0, 0.8, size=x.shape)
    x_thresh = x_noisy > .0

    # create unaries
    unaries = x_noisy
    # as we convert to int, we need to multipy to get sensible values
    unaries = np.dstack([-unaries, unaries])
    # create potts pairwise
    pairwise = np.eye(2)

    # do simple cut
    result = np.argmax(simple_grid(unaries, pairwise)[0], axis=-1)

    # use the general graph algorithm
    # first, we construct the grid graph
    inds = np.arange(x.size).reshape(x.shape)
    horz = np.c_[inds[:, :-1].ravel(), inds[:, 1:].ravel()]
    vert = np.c_[inds[:-1, :].ravel(), inds[1:, :].ravel()]
    edges = np.vstack([horz, vert])

    # we flatten the unaries
    pairwise_per_edge = np.repeat(pairwise[np.newaxis, :, :],
                                  edges.shape[0],
                                  axis=0)
    result_graph = np.argmax(general_graph(unaries.reshape(-1, 2), edges,
                                           pairwise_per_edge)[0],
                             axis=-1)

    # plot results
    if plot:
        import matplotlib.pyplot as plt
        plt.figure(figsize=(9, 8))
        plt.suptitle("Binary distribution", size=20)
        plt.subplot(231, title="original")
        plt.imshow(x, interpolation='nearest')
        plt.subplot(232, title="noisy version")
        plt.imshow(x_noisy, interpolation='nearest')
        plt.subplot(234, title="thresholding result")
        plt.imshow(x_thresh, interpolation='nearest')
        plt.subplot(235, title="cut_simple")
        plt.imshow(result, interpolation='nearest')
        plt.subplot(236, title="cut_from_graph")
        plt.imshow(result_graph.reshape(x.shape), interpolation='nearest')
        plt.tight_layout()
        plt.show()
    else:
        print(result_graph)
Ejemplo n.º 7
0
def example_binary(plot=True):
    # generate trivial data
    x = np.ones((10, 10))
    x[:, 5:] = -1
    x_noisy = x + np.random.normal(0, 0.8, size=x.shape)
    x_thresh = x_noisy > .0

    # create unaries
    unaries = x_noisy
    # as we convert to int, we need to multipy to get sensible values
    unaries = np.dstack([-unaries, unaries])
    # create potts pairwise
    pairwise = np.eye(2)

    # do simple cut
    result = np.argmax(simple_grid(unaries, pairwise)[0], axis=-1)

    # use the general graph algorithm
    # first, we construct the grid graph
    inds = np.arange(x.size).reshape(x.shape)
    horz = np.c_[inds[:, :-1].ravel(), inds[:, 1:].ravel()]
    vert = np.c_[inds[:-1, :].ravel(), inds[1:, :].ravel()]
    edges = np.vstack([horz, vert])

    # we flatten the unaries
    pairwise_per_edge = np.repeat(pairwise[np.newaxis, :, :], edges.shape[0],
                                  axis=0)
    result_graph = np.argmax(general_graph(unaries.reshape(-1, 2), edges,
                                           pairwise_per_edge)[0], axis=-1)

    # plot results
    if plot:
        import matplotlib.pyplot as plt
        plt.figure(figsize=(9, 8))
        plt.suptitle("Binary distribution", size=20)
        plt.subplot(231, title="original")
        plt.imshow(x, interpolation='nearest')
        plt.subplot(232, title="noisy version")
        plt.imshow(x_noisy, interpolation='nearest')
        plt.subplot(234, title="thresholding result")
        plt.imshow(x_thresh, interpolation='nearest')
        plt.subplot(235, title="cut_simple")
        plt.imshow(result, interpolation='nearest')
        plt.subplot(236, title="cut_from_graph")
        plt.imshow(result_graph.reshape(x.shape), interpolation='nearest')
        plt.tight_layout()
        plt.show()
    else:
        print(result_graph)
Ejemplo n.º 8
0
def test_general_graph_multitype():
    empty = np.zeros((0, 0))

    unaries = [np.array([[10, 11]]), np.array([[1000, 1100, 1200]])]
    edges = [empty, np.array([[0, 0]]), empty, empty]
    edge_weights = [
        empty,
        np.array([[[.00, .01, .02], [.10, .11, .12]]]), empty, empty
    ]

    ret = general_graph(unaries, edges, edge_weights, verbose=1)

    marginals, edge_marginals, value, solver_status = ret
    assert_array_almost_equal(marginals[0], np.array([[0, 1]]))
    assert_array_almost_equal(marginals[1], np.array([[0, 0, 1]]))

    assert_array_almost_equal(edge_marginals[0], np.zeros((0, 4)))
    assert_array_almost_equal(edge_marginals[1].reshape(2, 3),
                              np.array([[0, 0, 0], [0, 0, 1]]), 5)
    assert_array_almost_equal(edge_marginals[2], np.zeros((0, 6)))
    assert_array_almost_equal(edge_marginals[3], np.zeros((0, 9)))
Ejemplo n.º 9
0
def test_general_graph_multitype():
    empty = np.zeros((0, 0))

    unaries = [np.array([[10, 11]]),
               np.array([[1000, 1100, 1200]])]
    edges = [empty, np.array([[0, 0]]), empty, empty]
    edge_weights = [empty,
                    np.array([[[.00, .01, .02],
                               [.10, .11, .12]]]),
                    empty,
                    empty]

    ret = general_graph(unaries, edges, edge_weights, verbose=1)

    marginals, edge_marginals, value, solver_status = ret
    assert_array_almost_equal(marginals[0], np.array([[0, 1]]))
    assert_array_almost_equal(marginals[1], np.array([[0, 0, 1]]))

    assert_array_almost_equal(edge_marginals[0], np.zeros((0, 4)))
    assert_array_almost_equal(edge_marginals[1].reshape(2, 3),
                              np.array([[0, 0, 0],
                                        [0, 0, 1]]), 5)
    assert_array_almost_equal(edge_marginals[2], np.zeros((0, 6)))
    assert_array_almost_equal(edge_marginals[3], np.zeros((0, 9)))
Ejemplo n.º 10
0
def inference_ad3(unary_potentials,
                  pairwise_potentials,
                  edges,
                  relaxed=False,
                  verbose=0,
                  return_energy=False,
                  branch_and_bound=False,
                  inference_exception=None):
    """Inference with AD3 dual decomposition subgradient solver.

    Parameters
    ----------
    unary_potentials : nd-array, shape (n_nodes, n_states)
        Unary potentials of energy function.

    pairwise_potentials : nd-array, shape (n_states, n_states) 
                        or (n_states, n_states, n_edges).
        Pairwise potentials of energy function.
        If the first case, edge potentials are assumed to be the same for all 
        edges.
        In the second case, the sequence needs to correspond to the edges.

    edges : nd-array, shape (n_edges, 2)
        Graph edges for pairwise potentials, given as pair of node indices. As
        pairwise potentials are not assumed to be symmetric, the direction of
        the edge matters.

    relaxed : bool (default=False)
        Whether to return the relaxed solution (``True``) or round to the next
        integer solution (``False``).

    verbose : int (default=0)
        Degree of verbosity for solver.

    return_energy : bool (default=False)
        Additionally return the energy of the returned solution (according to
        the solver).  If relaxed=False, this is the energy of the relaxed, not
        the rounded solution.

    branch_and_bound : bool (default=False)
        Whether to attempt to produce an integral solution using
        branch-and-bound.

    Returns
    -------
    labels : nd-array
        Approximate (usually) MAP variable assignment.
        If relaxed=False, this is a tuple of unary and edge 'marginals'.
        
    Code updated on Feb 2017 to deal with multiple node types, by JL Meunier
    , for the EU READ project (grant agreement No 674943)
    
    """
    import ad3
    bMultiType = isinstance(unary_potentials, list)
    if bMultiType:
        res = ad3.general_graph(unary_potentials,
                                edges,
                                pairwise_potentials,
                                verbose=verbose,
                                n_iterations=4000,
                                exact=branch_and_bound)
    else:
        #usual code
        n_states, pairwise_potentials = \
            _validate_params(unary_potentials, pairwise_potentials, edges)
        unaries = unary_potentials.reshape(-1, n_states)
        res = ad3.general_graph(unaries,
                                edges,
                                pairwise_potentials,
                                verbose=verbose,
                                n_iterations=4000,
                                exact=branch_and_bound)

    unary_marginals, pairwise_marginals, energy, solver_status = res
    if verbose:
        print(solver_status)

    if solver_status in ["fractional", "unsolved"] and relaxed:
        if bMultiType:
            y = (unary_marginals, pairwise_marginals)  #those two are lists
        else:
            #usual code
            unary_marginals = unary_marginals.reshape(unary_potentials.shape)
            y = (unary_marginals, pairwise_marginals)
        #print solver_status, pairwise_marginals
    else:
        if bMultiType:
            #we now get a list of unary marginals
            if inference_exception and solver_status in [
                    "fractional", "unsolved"
            ]:
                raise InferenceException(solver_status)
            ly = list()
            _cum_n_states = 0
            for unary_marg in unary_marginals:
                ly.append(_cum_n_states + np.argmax(unary_marg, axis=-1))
                # number of states for that type
                _cum_n_states += unary_marg.shape[1]
            y = np.hstack(ly)
        else:
            #usual code
            y = np.argmax(unary_marginals, axis=-1)

    if return_energy:
        return y, -energy
    return y
Ejemplo n.º 11
0
def inference_ad3(unary_potentials, pairwise_potentials, edges, relaxed=False,
                  verbose=0, return_energy=False, branch_and_bound=False,
                  inference_exception=None):
    """Inference with AD3 dual decomposition subgradient solver.

    Parameters
    ----------
    unary_potentials : nd-array, shape (n_nodes, n_states)
        Unary potentials of energy function.

    pairwise_potentials : nd-array, shape (n_states, n_states) 
                        or (n_states, n_states, n_edges).
        Pairwise potentials of energy function.
        If the first case, edge potentials are assumed to be the same for all 
        edges.
        In the second case, the sequence needs to correspond to the edges.

    edges : nd-array, shape (n_edges, 2)
        Graph edges for pairwise potentials, given as pair of node indices. As
        pairwise potentials are not assumed to be symmetric, the direction of
        the edge matters.

    relaxed : bool (default=False)
        Whether to return the relaxed solution (``True``) or round to the next
        integer solution (``False``).

    verbose : int (default=0)
        Degree of verbosity for solver.

    return_energy : bool (default=False)
        Additionally return the energy of the returned solution (according to
        the solver).  If relaxed=False, this is the energy of the relaxed, not
        the rounded solution.

    branch_and_bound : bool (default=False)
        Whether to attempt to produce an integral solution using
        branch-and-bound.

    Returns
    -------
    labels : nd-array
        Approximate (usually) MAP variable assignment.
        If relaxed=False, this is a tuple of unary and edge 'marginals'.
        
    Code updated on Feb 2017 to deal with multiple node types, by JL Meunier
    , for the EU READ project (grant agreement No 674943)
    
    """
    import ad3
    bMultiType = isinstance(unary_potentials, list)
    if bMultiType:
        res = ad3.general_graph(unary_potentials, edges, pairwise_potentials
                                , verbose=verbose
                                , n_iterations=4000, exact=branch_and_bound)
    else:
        #usual code
        n_states, pairwise_potentials = \
            _validate_params(unary_potentials, pairwise_potentials, edges)
        unaries = unary_potentials.reshape(-1, n_states)
        res = ad3.general_graph(unaries, edges, pairwise_potentials
                                , verbose=verbose, n_iterations=4000
                                , exact=branch_and_bound)
        
    unary_marginals, pairwise_marginals, energy, solver_status = res
    if verbose:
        print(solver_status)

    if solver_status in ["fractional", "unsolved"] and relaxed:
        if bMultiType:
            y = (unary_marginals, pairwise_marginals)  #those two are lists
        else:
            #usual code
            unary_marginals = unary_marginals.reshape(unary_potentials.shape)
            y = (unary_marginals, pairwise_marginals)
        #print solver_status, pairwise_marginals
    else:
        if bMultiType:
            #we now get a list of unary marginals
            if inference_exception and solver_status in ["fractional"
                                                         , "unsolved"]:
                raise InferenceException(solver_status)
            ly = list()
            _cum_n_states = 0
            for unary_marg in unary_marginals:
                ly.append( _cum_n_states + np.argmax(unary_marg, axis=-1) )
                # number of states for that type
                _cum_n_states += unary_marg.shape[1]  
            y = np.hstack(ly)            
        else:
            #usual code
            y = np.argmax(unary_marginals, axis=-1)
        
    if return_energy:
        return y, -energy
    return y
Ejemplo n.º 12
0
def inference_ad3(unary_potentials,
                  pairwise_potentials,
                  edges,
                  relaxed=False,
                  verbose=0,
                  return_energy=False,
                  branch_and_bound=False,
                  n_iterations=4000):
    """Inference with AD3 dual decomposition subgradient solver.

    Parameters
    ----------
    unary_potentials : nd-array
        Unary potentials of energy function.

    pairwise_potentials : nd-array
        Pairwise potentials of energy function.

    edges : nd-array
        Edges of energy function.

    relaxed : bool (default=False)
        Whether to return the relaxed solution (``True``) or round to the next
        integer solution (``False``).

    verbose : int (default=0)
        Degree of verbosity for solver.

    return_energy : bool (default=False)
        Additionally return the energy of the returned solution (according to
        the solver).  If relaxed=False, this is the energy of the relaxed, not
        the rounded solution.

    branch_and_bound : bool (default=False)
        Whether to attempt to produce an integral solution using
        branch-and-bound.

    Returns
    -------
    labels : nd-array
        Approximate (usually) MAP variable assignment.
        If relaxed=False, this is a tuple of unary and edge 'marginals'.
    """
    import ad3
    n_states, pairwise_potentials = \
        _validate_params(unary_potentials, pairwise_potentials, edges)

    unaries = unary_potentials.reshape(-1, n_states)
    res = ad3.general_graph(unaries,
                            edges,
                            pairwise_potentials,
                            verbose=1,
                            n_iterations=n_iterations,
                            exact=branch_and_bound)
    unary_marginals, pairwise_marginals, energy, solver_status = res
    if verbose:
        print solver_status[0],

    if solver_status in ["fractional", "unsolved"] and relaxed:
        unary_marginals = unary_marginals.reshape(unary_potentials.shape)
        y = (unary_marginals, pairwise_marginals)
    else:
        y = np.argmax(unary_marginals, axis=-1)
    if return_energy:
        return y, -energy
    return y