<SYSTEM_TASK:>
Solve the following problem using Python, implementing the functions described below, one line at a time
<END_TASK>
<USER_TASK:>
Description:
 def weighted_random(samples, chains):
 """Determine the sample values of chains by weighed random choice. Args: samples (array_like):
 Samples as a nS x nV array_like object where nS is the number of samples and nV is the number of variables. The values should all be 0/1 or -1/+1. chains (list[array_like]):
 List of chains of length nC where nC is the number of chains. Each chain should be an array_like collection of column indices in samples. Returns: tuple: A 2-tuple containing: :obj:`numpy.ndarray`: A nS x nC array of unembedded samples. The array has dtype 'int8'. Where there is a chain break, the value is chosen randomly, weighted by frequency of the chain's value. :obj:`numpy.ndarray`: Equivalent to :code:`np.arange(nS)` because all samples are kept and no samples are added. Examples: This example unembeds samples from a target graph that chains nodes 0 and 1 to represent one source node and nodes 2, 3, and 4 to represent another. The sample has broken chains for both source nodes. array([[1, 1]], dtype=int8) array([0, 1]) """

    samples = np.asarray(samples)
    if samples.ndim != 2:
        raise ValueError("expected samples to be a numpy 2D array")

    # it sufficies to choose a random index from each chain and use that to construct the matrix
    idx = [np.random.choice(chain) for chain in chains]

    num_samples, num_variables = samples.shape
    return samples[:, idx], np.arange(num_samples)