Пример #1
0
def ndcg(labels, predictions,
                  metrics_collections=None,
                  updates_collections=None,
                  name=None,
                  top_k_int=1,
                  use_predicted_order=False):
  # pylint: disable=unused-argument
  """
  Compute full normalized discounted cumulative gain (ndcg) based on predictions
    ndcg = dcg_k/idcg_k, k is a cut off ranking postion
    There are a few variants of ndcg
    The dcg (discounted cumulative gain) formula used in 
    twml.contrib.metrics.ndcg is
    \sum_{i=1}^k \frac{2^{relevance\_score} -1}{\log_{2}(i + 1)}
    k is the length of items to be ranked in a batch/query
    Notice that whether k will be replaced with a fixed value requires discussions 
    The scores in predictions are transformed to order and relevance scores to calculate ndcg
    A relevance score means how relevant a DataRecord is to a particular query       
  Args:
    labels: the ground truth value.
    predictions: the predicted values, whose shape must match labels. Ignored for CTR computation.
    metrics_collections: optional list of collections to add this metric into.
    updates_collections: optional list of collections to add the associated update_op into.
    name: an optional variable_scope name.

  Return:
    ndcg: A `Tensor` representing the ndcg score.
    update_op: A update operation used to accumulate data into this metric.
  """
  with tf.variable_scope(name, 'ndcg', (labels, predictions)):
    label_scores = tf.to_float(labels, name='label_to_float')
    predicted_scores = tf.to_float(predictions, name='predictions_to_float')

    total_ndcg = _metric_variable([], dtypes.float32, name='total_ndcg')
    count_query = _metric_variable([], dtypes.float32, name='query_count')

    # actual ndcg cutoff position top_k_int
    max_prediction_size = array_ops.size(predicted_scores)
    top_k_int = tf.minimum(max_prediction_size, top_k_int)
    # the ndcg score of the batch
    ndcg = math_fns.cal_ndcg(label_scores,
      predicted_scores, top_k_int=top_k_int, use_predicted_order=use_predicted_order)
    # add ndcg of the current batch to total_ndcg
    update_total_op = state_ops.assign_add(total_ndcg, ndcg)
    with ops.control_dependencies([ndcg]):
      # count_query stores the number of queries
      # count_query increases by 1 for each batch/query
      update_count_op = state_ops.assign_add(count_query, 1)

    mean_ndcg = math_fns.safe_div(total_ndcg, count_query, 'mean_ndcg')
    update_op = math_fns.safe_div(update_total_op, update_count_op, 'update_mean_ndcg_op')

    if metrics_collections:
      ops.add_to_collections(metrics_collections, mean_ndcg)

    if updates_collections:
      ops.add_to_collections(updates_collections, update_op)

    return mean_ndcg, update_op
Пример #2
0
def err(labels, predictions,
                  metrics_collections=None,
                  updates_collections=None,
                  name=None,
                  top_k_int=1,
                  use_predicted_order=False):
  # pylint: disable=unused-argument
  """
  Compute Expected Reciprocal Rank
    The scores in predictions are transformed to order and relevance scores to calculate ndcg
    A relevance score means how relevant a DataRecord is to a particular query       
  Args:
    labels: the ground truth value.
    predictions: the predicted values, whose shape must match labels. Ignored for CTR computation.
    metrics_collections: optional list of collections to add this metric into.
    updates_collections: optional list of collections to add the associated update_op into.
    name: an optional variable_scope name.

  Return:
    err: A `Tensor` representing the err score.
    update_op: A update operation used to accumulate data into this metric.
  """
  with tf.variable_scope(name, 'err', (labels, predictions)):
    label_scores = tf.to_float(labels, name='label_to_float_err')
    predicted_scores = tf.to_float(predictions, name='predictions_to_float_err')

    total_err = _metric_variable([], dtypes.float32, name='total_err')
    count_query = _metric_variable([], dtypes.float32, name='query_count_err')

    # actual err cutoff position top_k_int is equal to max_prediction_size
    max_prediction_size = array_ops.size(predicted_scores)
    top_k_int = tf.minimum(max_prediction_size, top_k_int)
    # the err score of the batch

    err_full = math_fns.cal_err(labels,
      predicted_scores, top_k_int=top_k_int, use_predicted_order=use_predicted_order)

    # add err of the current batch to total_err
    update_total_op = state_ops.assign_add(total_err, err_full)
    with ops.control_dependencies([err_full]):
      # count_query stores the number of queries
      # count_query increases by 1 for each batch/query
      update_count_op = state_ops.assign_add(count_query, 1)

    mean_err = math_fns.safe_div(total_err, count_query, 'mean_err')
    update_op = math_fns.safe_div(update_total_op, update_count_op, 'update_mean_err_op')

    if metrics_collections:
      ops.add_to_collections(metrics_collections, mean_err)

    if updates_collections:
      ops.add_to_collections(updates_collections, update_op)

    return mean_err, update_op
Пример #3
0
def _get_attentions(raw_scores):
    """
  Used in attention weights in AttRank loss
  for a query/batch/batchPreidictionRequest
  (a rectified softmax function)
  """
    not_consider = tf.less_equal(raw_scores, 0)
    mask = tf.ones(tf.shape(raw_scores)) - tf.cast(not_consider,
                                                   dtype=tf.float32)
    mask = tf.cast(mask, dtype=tf.float32)
    expon_labels = mask * tf.exp(raw_scores)

    expon_label_sum = tf.reduce_sum(expon_labels)
    # expon_label_sum is safe as a denominator
    attentions = math_fns.safe_div(expon_labels, expon_label_sum)
    return attentions