def precision_at_k(k, relevant, retrieved, ignore = []):
    """ Computes the precision among the top `k` retrieval results for a particular query.
    
    k - Number of best-scoring results to be considered. Instead of a single number, a list of `k` values may be given
        to evaluate precision at. In this case, this function will return a list of corresponding precisions as well.
    relevant - Ground-Truth: Set of IDs relevant to the query.
    retrieved - Ranked list of retrieved IDs.
    ignore - Optionally, a set of IDs to be ignored, i.e., to be counted neither as true nor as false positive.
    
    Returns: Precision@k, given as a single number or a list, depending on the value of `k`
    """
    
    ks = [k] if isinstance(k, int) else list(k)
    ks.sort()
    k_index = 0
    
    precisions = []
    
    rank, tp = 0, 0
    for ret in retrieved:
        if ret not in ignore:
            if ret in relevant:
                tp += 1
            rank += 1
            while (k_index < len(ks)) and (rank >= ks[k_index]):
                precisions.append(float(tp) / float(rank))
                k_index += 1
            if k_index >= len(ks):
                break
    return precisions[0] if isinstance(k, int) else precisions