jiahuimbzuai/CoQuIR huggingface dataset:
//  [python]
def _learning_rate_decay(hparams, warmup_steps=0):
  """Learning rate decay multiplier."""
  scheme = hparams.learning_rate_decay_scheme
  warmup_steps = tf.to_float(warmup_steps)
  global_step = _global_step(hparams)

  if not scheme or scheme == "none":
    return tf.constant(1.)

  tf.logging.info("Applying learning rate decay: %s.", scheme)

  if scheme == "exp":
    decay_steps = hparams.learning_rate_decay_steps
    p = (global_step - warmup_steps) / decay_steps
    if hparams.learning_rate_decay_staircase:
      p = tf.floor(p)
    return tf.pow(hparams.learning_rate_decay_rate, p)

  if scheme == "piecewise":
    return _piecewise_learning_rate(global_step,
                                    hparams.learning_rate_boundaries,
                                    hparams.learning_rate_multiples)

  if scheme == "cosine":
    cycle_steps = hparams.learning_rate_cosine_cycle_steps
    cycle_position = global_step % (2 * cycle_steps)
    cycle_position = cycle_steps - tf.abs(cycle_steps - cycle_position)
    return 0.5 * (1 + tf.cos(np.pi * cycle_position / cycle_steps))

  if scheme == "cyclelinear10x":
    # Cycle the rate linearly by 10x every warmup_steps, up and down.
    cycle_steps = warmup_steps
    cycle_position = global_step % (2 * cycle_steps)
    cycle_position = tf.to_float(  # Normalize to the interval [-1, 1].
        cycle_position - cycle_steps) / float(cycle_steps)
    cycle_position = 1.0 - tf.abs(cycle_position)  # 0 to 1 and back to 0.
    return (cycle_position + 0.1) * 3.0  # 10x difference each cycle (0.3-3).

  if scheme == "sqrt":
    return _legacy_sqrt_decay(global_step - warmup_steps)

  raise ValueError("Unrecognized learning rate decay scheme: %s" %
                   hparams.learning_rate_decay_scheme)
//  [python]
def _learning_rate_decay(hparams, warmup_steps=0):
  """Learning rate decay multiplier."""
  scheme = hparams.learning_rate_decay_scheme
  warmup_steps = tf.cast(warmup_steps, tf.float32)
  global_step = _global_step(hparams)

  if not scheme or scheme == "none":
    return tf.constant(1.)

  tf.logging.info("Applying learning rate decay: %s.", scheme)

  if scheme == "exp":
    decay_steps = hparams.learning_rate_decay_steps
    p = (global_step - warmup_steps) / decay_steps
    if hparams.learning_rate_decay_staircase:
      p = tf.floor(p)
    return tf.pow(hparams.learning_rate_decay_rate, p)

  if scheme == "piecewise":
    return _piecewise_learning_rate(global_step,
                                    hparams.learning_rate_boundaries,
                                    hparams.learning_rate_multiples)

  if scheme == "cosine":
    cycle_steps = hparams.learning_rate_cosine_cycle_steps
    cycle_position = global_step % (2 * cycle_steps)
    cycle_position = cycle_steps - tf.abs(cycle_steps - cycle_position)
    return 0.5 * (1 + tf.cos(np.pi * cycle_position / cycle_steps))

  if scheme == "cyclelinear10x":
    # Cycle the rate linearly by 10x every warmup_steps, up and down.
    cycle_steps = warmup_steps
    cycle_position = global_step % (2 * cycle_steps)
    cycle_position = tf.cast(  # Normalize to the interval [-1, 1].
        cycle_position - cycle_steps, tf.float32) / float(cycle_steps)
    cycle_position = 1.0 - tf.abs(cycle_position)  # 0 to 1 and back to 0.
    return (cycle_position + 0.1) * 3.0  # 10x difference each cycle (0.3-3).

  if scheme == "sqrt":
    return _legacy_sqrt_decay(global_step - warmup_steps)

  raise ValueError("Unrecognized learning rate decay scheme: %s" %
                   hparams.learning_rate_decay_scheme)
//  [python]
def safe_exp(w, thresh):
  """Safe exponential function for tensors."""

  slope = np.exp(thresh)
  with tf.name_scope('safe_exponential'):
    lin_region = tf.to_float(w > thresh)

    lin_out = slope * (w - thresh + 1.)
    exp_out = tf.exp(w)

    out = lin_region * lin_out + (1. - lin_region) * exp_out
  return out
//  [python]
def safe_exp(w, thresh):
  """Safe exponential function for tensors."""

  slope = np.exp(thresh)
  with tf.name_scope('safe_exponential'):
    lin_region = tf.cast(w > thresh, tf.float32)

    lin_out = slope * (w - thresh + 1.)
    exp_out = tf.exp(w)

    out = lin_region * lin_out + (1. - lin_region) * exp_out
  return out
//  [python]
def compute_Z(self, num_samples):  # pylint: disable=invalid-name
    r"""Returns log(\sum_i a(z_i) / num_samples)."""
    z_s = self.proposal.sample(num_samples)  # [num_samples, data_dim]
    # Compute log a(z) for zs sampled from proposal
    log_a_z_s = tf.squeeze(self.accept_fn(z_s - self.data_mean),
                           axis=-1)  # [num_samples]
    log_Z = tf.reduce_logsumexp(log_a_z_s) - tf.log(  # pylint: disable=invalid-name
        tf.to_float(num_samples))  # []
    return log_Z
//  [python]
def compute_Z(self, num_samples):  # pylint: disable=invalid-name
    r"""Returns log(\sum_i a(z_i) / num_samples)."""
    z_s = self.proposal.sample(num_samples)  # [num_samples, data_dim]
    # Compute log a(z) for zs sampled from proposal
    log_a_z_s = tf.squeeze(self.accept_fn(z_s - self.data_mean),
                           axis=-1)  # [num_samples]
    log_Z = tf.reduce_logsumexp(log_a_z_s) - tf.log(  # pylint: disable=invalid-name
        tf.cast(num_samples, dtype=tf.float32))  # []
    return log_Z
//  [python]
def input_fn_builder(input_file, seq_length, is_training, drop_remainder):
  """Creates an `input_fn` closure to be passed to TPUEstimator."""

  name_to_features = {
      "unique_ids": tf.FixedLenFeature([], tf.int64),
      "input_ids": tf.FixedLenFeature([seq_length], tf.int64),
      "input_mask": tf.FixedLenFeature([seq_length], tf.int64),
      "segment_ids": tf.FixedLenFeature([seq_length], tf.int64),
  }

  if is_training:
    name_to_features["label_ids"] = tf.FixedLenFeature([], tf.int64)

  def _decode_record(record, name_to_features):
    """Decodes a record to a TensorFlow example."""
    example = tf.parse_single_example(record, name_to_features)

    # tf.Example only supports tf.int64, but the TPU only supports tf.int32.
    # So cast all int64 to int32.
    for name in list(example.keys()):
      t = example[name]
      if t.dtype == tf.int64:
        t = tf.to_int32(t)
      example[name] = t

    return example

  def input_fn(params):
    """The actual input function."""
    batch_size = params["batch_size"]

    # For training, we want a lot of parallel reading and shuffling.
    # For eval, we want no shuffling and parallel reading doesn't matter.
    d = tf.data.TFRecordDataset(input_file)
    if is_training:
      d = d.repeat()
      d = d.shuffle(buffer_size=100)

    d = d.apply(
        tf.data.experimental.map_and_batch(
            lambda record: _decode_record(record, name_to_features),
            batch_size=batch_size,
            drop_remainder=drop_remainder))

    return d

  return input_fn
//  [python]
def input_fn_builder(input_file, seq_length, is_training, drop_remainder):
  """Creates an `input_fn` closure to be passed to TPUEstimator."""

  name_to_features = {
      "unique_ids": tf.FixedLenFeature([], tf.int64),
      "input_ids": tf.FixedLenFeature([seq_length], tf.int64),
      "input_mask": tf.FixedLenFeature([seq_length], tf.int64),
      "segment_ids": tf.FixedLenFeature([seq_length], tf.int64),
  }

  if is_training:
    name_to_features["label_ids"] = tf.FixedLenFeature([], tf.int64)

  def _decode_record(record, name_to_features):
    """Decodes a record to a TensorFlow example."""
    example = tf.parse_single_example(record, name_to_features)

    # tf.Example only supports tf.int64, but the TPU only supports tf.int32.
    # So cast all int64 to int32.
    for name in list(example.keys()):
      t = example[name]
      if t.dtype == tf.int64:
        t = tf.cast(t, tf.int32)
      example[name] = t

    return example

  def input_fn(params):
    """The actual input function."""
    batch_size = params["batch_size"]

    # For training, we want a lot of parallel reading and shuffling.
    # For eval, we want no shuffling and parallel reading doesn't matter.
    d = tf.data.TFRecordDataset(input_file)
    if is_training:
      d = d.repeat()
      d = d.shuffle(buffer_size=100)

    d = d.apply(
        tf.data.experimental.map_and_batch(
            lambda record: _decode_record(record, name_to_features),
            batch_size=batch_size,
            drop_remainder=drop_remainder))

    return d

  return input_fn
//  [python]
def get_resize_scale(self, height, width):
        """
        Get the resize scale so that the shortest side is `smallest_side`
        """
        smallest_side = tf.convert_to_tensor(self.smallest_side, dtype=tf.int32)

        height = tf.to_float(height)
        width = tf.to_float(width)
        smallest_side = tf.to_float(smallest_side)

        scale = tf.cond(
                tf.greater(height, width),
                lambda: smallest_side / width,
                lambda: smallest_side / height)
        return scale
//  [python]
def get_resize_scale(self, height, width):
        """
        Get the resize scale so that the shortest side is `smallest_side`
        """
        smallest_side = tf.convert_to_tensor(self.smallest_side, dtype=tf.int32)

        height = tf.cast(height, tf.float32)
        width = tf.cast(width, tf.float32)
        smallest_side = tf.cast(smallest_side, tf.float32)

        scale = tf.cond(
                tf.greater(height, width),
                lambda: smallest_side / width,
                lambda: smallest_side / height)
        return scale
//  [python]
def sample(self, num_samples=1):
    """Sample from the model."""

    def while_body(t, z, accept):
      """Truncated rejection sampling."""
      new_z = self.proposal.sample(num_samples)
      accept_prob = tf.squeeze(tf.exp(self.accept_fn(new_z - self.data_mean)),
                               axis=-1)
      new_accept = tf.math.less_equal(
          tf.random_uniform(shape=[num_samples], minval=0., maxval=1.),
          accept_prob)
      force_accept = tf.math.greater_equal(
          tf.to_float(t),
          tf.to_float(self.T) - 1.)
      new_accept = tf.math.logical_or(new_accept, force_accept)
      accepted = tf.logical_or(accept, new_accept)
      swap = tf.math.logical_and(tf.math.logical_not(accept), new_accept)
      z = tf.where(swap, new_z, z)
      return t + 1, z, accepted

    def while_cond(unused_t, unused_z, accept):
      return tf.reduce_any(tf.logical_not(accept))

    shape = [num_samples] + self.data_dim
    z0 = tf.zeros(shape, dtype=self.dtype)
    accept0 = tf.constant(False, shape=[num_samples])
    _, zs, _ = tf.while_loop(while_cond, while_body, loop_vars=(0, z0, accept0))
    return zs
//  [python]
def sample(self, num_samples=1):
    """Sample from the model."""

    def while_body(t, z, accept):
      """Truncated rejection sampling."""
      new_z = self.proposal.sample(num_samples)
      accept_prob = tf.squeeze(tf.exp(self.accept_fn(new_z - self.data_mean)),
                               axis=-1)
      new_accept = tf.math.less_equal(
          tf.random_uniform(shape=[num_samples], minval=0., maxval=1.),
          accept_prob)
      force_accept = tf.math.greater_equal(
          tf.cast(t, tf.float32),
          tf.cast(self.T, tf.float32) - 1.)
      new_accept = tf.math.logical_or(new_accept, force_accept)
      accepted = tf.logical_or(accept, new_accept)
      swap = tf.math.logical_and(tf.math.logical_not(accept), new_accept)
      z = tf.where(swap, new_z, z)
      return t + 1, z, accepted

    def while_cond(unused_t, unused_z, accept):
      return tf.reduce_any(tf.logical_not(accept))

    shape = [num_samples] + self.data_dim
    z0 = tf.zeros(shape, dtype=self.dtype)
    accept0 = tf.constant(False, shape=[num_samples])
    _, zs, _ = tf.while_loop(while_cond, while_body, loop_vars=(0, z0, accept0))
    return zs
//  [python]
def log_prob(self, data, log_q_data=None, num_samples=1):
    """Compute log likelihood estimate."""
    # Compute log a(z), log pi(z), and log q(z)
    log_a_z_r = tf.squeeze(self.accept_fn(data - self.data_mean),
                           axis=-1)  # [batch_size]
    # [batch_size]
    try:
      # Try giving the proposal lower bound num_samples if it can use it.
      log_pi_z_r = self.proposal.log_prob(data, num_samples=num_samples)
    except TypeError:
      log_pi_z_r = self.proposal.log_prob(data)

    tf.summary.histogram("log_energy_data", log_a_z_r)
    if not self.is_eval:
      # Sample zs from proposal to estimate Z
      z_s = self.proposal.sample(self.k)  # [K, data_dim]
      # Compute log a(z) for zs sampled from proposal
      log_a_z_s = tf.squeeze(self.accept_fn(z_s - self.data_mean),
                             axis=-1)  # [K]
      tf.summary.histogram("log_energy_proposal", log_a_z_s)

      # pylint: disable=invalid-name
      log_ZS = tf.reduce_logsumexp(log_a_z_s)  # []
      log_Z_curr_avg = log_ZS - tf.log(tf.to_float(self.k))

      if log_q_data is not None:
        # This may only be valid when log pi is exact (i.e., not a lower bound).
        Z_curr_avg = (1. / (self.k + 1.)) * (
            tf.exp(log_ZS) +
            tf.exp(log_a_z_r + tf.stop_gradient(log_pi_z_r - log_q_data)))
      else:
        Z_curr_avg = tf.exp(log_Z_curr_avg)

      self.Z_smooth = (
          self.ema_decay * self.Z_ema + (1 - self.ema_decay) * Z_curr_avg)

      # In forward pass, log Z is log of the smoothed ema version of Z
      # In backward pass it is the current estimate of log Z, log_Z_curr_avg
      Z = Z_curr_avg + tf.stop_gradient(self.Z_smooth - Z_curr_avg)
      tf.summary.scalar("Z", tf.reduce_mean(Z))
    else:
      Z = self.Z_estimate  # pylint: disable=invalid-name

    # pylint: enable=invalid-name
    alpha = tf.pow(1. - Z, self.T - 1)
    log_prob = log_pi_z_r + tf.log(tf.exp(log_a_z_r) * (1. - alpha) / Z + alpha)
    return log_prob
//  [python]
def log_prob(self, data, log_q_data=None, num_samples=1):
    """Compute log likelihood estimate."""
    # Compute log a(z), log pi(z), and log q(z)
    log_a_z_r = tf.squeeze(self.accept_fn(data - self.data_mean),
                           axis=-1)  # [batch_size]
    # [batch_size]
    try:
      # Try giving the proposal lower bound num_samples if it can use it.
      log_pi_z_r = self.proposal.log_prob(data, num_samples=num_samples)
    except TypeError:
      log_pi_z_r = self.proposal.log_prob(data)

    tf.summary.histogram("log_energy_data", log_a_z_r)
    if not self.is_eval:
      # Sample zs from proposal to estimate Z
      z_s = self.proposal.sample(self.k)  # [K, data_dim]
      # Compute log a(z) for zs sampled from proposal
      log_a_z_s = tf.squeeze(self.accept_fn(z_s - self.data_mean),
                             axis=-1)  # [K]
      tf.summary.histogram("log_energy_proposal", log_a_z_s)

      # pylint: disable=invalid-name
      log_ZS = tf.reduce_logsumexp(log_a_z_s)  # []
      log_Z_curr_avg = log_ZS - tf.log(tf.cast(self.k, tf.float32))

      if log_q_data is not None:
        # This may only be valid when log pi is exact (i.e., not a lower bound).
        Z_curr_avg = (1. / (self.k + 1.)) * (
            tf.exp(log_ZS) +
            tf.exp(log_a_z_r + tf.stop_gradient(log_pi_z_r - log_q_data)))
      else:
        Z_curr_avg = tf.exp(log_Z_curr_avg)

      self.Z_smooth = (
          self.ema_decay * self.Z_ema + (1 - self.ema_decay) * Z_curr_avg)

      # In forward pass, log Z is log of the smoothed ema version of Z
      # In backward pass it is the current estimate of log Z, log_Z_curr_avg
      Z = Z_curr_avg + tf.stop_gradient(self.Z_smooth - Z_curr_avg)
      tf.summary.scalar("Z", tf.reduce_mean(Z))
    else:
      Z = self.Z_estimate  # pylint: disable=invalid-name

    # pylint: enable=invalid-name
    alpha = tf.pow(1. - Z, self.T - 1)
    log_prob = log_pi_z_r + tf.log(tf.exp(log_a_z_r) * (1. - alpha) / Z + alpha)
    return log_prob
//  [python]
def features_to_nonpadding(features, inputs_or_targets = 'inputs'):
    """See transformer.features_to_nonpadding."""
    key = inputs_or_targets + '_segmentation'
    if features and key in features:
        return tf.minimum(tf.to_float(features[key]), 1.0)
    return None
//  [python]
def features_to_nonpadding(features, inputs_or_targets = 'inputs'):
    """See transformer.features_to_nonpadding."""
    key = inputs_or_targets + '_segmentation'
    if features and key in features:
        return tf.minimum(tf.cast(features[key], tf.float32), 1.0)
    return None
//  [python]
def testNegativeLogPerplexityMasked(self):
    predictions = np.random.randint(4, size=(12, 12, 12, 1))
    targets = np.random.randint(4, size=(12, 12, 12, 1))
    features = {
        'targets_mask': tf.to_float(tf.ones([12, 12]))
    }
    with self.test_session() as session:
      scores, _ = metrics.padded_neg_log_perplexity_with_masking(
          tf.one_hot(predictions, depth=4, dtype=tf.float32),
          tf.constant(targets, dtype=tf.int32),
          features)
      a = tf.reduce_mean(scores)
      session.run(tf.global_variables_initializer())
      actual = session.run(a)
    self.assertEqual(actual.shape, ())
//  [python]
def testNegativeLogPerplexityMasked(self):
    predictions = np.random.randint(4, size=(12, 12, 12, 1))
    targets = np.random.randint(4, size=(12, 12, 12, 1))
    features = {
        'targets_mask': tf.cast(tf.ones([12, 12]), tf.float32)
    }
    with self.test_session() as session:
      scores, _ = metrics.padded_neg_log_perplexity_with_masking(
          tf.one_hot(predictions, depth=4, dtype=tf.float32),
          tf.constant(targets, dtype=tf.int32),
          features)
      a = tf.reduce_mean(scores)
      session.run(tf.global_variables_initializer())
      actual = session.run(a)
    self.assertEqual(actual.shape, ())
//  [python]
def positional_encoding(inputs,
                        maxlen,
                        masking=True,
                        scope="positional_encoding"):
    '''Sinusoidal Positional_Encoding. See 3.5
    inputs: 3d tensor. (N, T, E)
    maxlen: scalar. Must be >= T
    masking: Boolean. If True, padding positions are set to zeros.
    scope: Optional scope for `variable_scope`.

    returns
    3d tensor that has the same shape as inputs.
    '''

    E = inputs.get_shape().as_list()[-1] # static
    N, T = tf.shape(inputs)[0], tf.shape(inputs)[1] # dynamic
    with tf.variable_scope(scope, reuse=tf.AUTO_REUSE):
        # position indices
        position_ind = tf.tile(tf.expand_dims(tf.range(T), 0), [N, 1]) # (N, T)

        # First part of the PE function: sin and cos argument
        position_enc = np.array([
            [pos / np.power(10000, (i-i%2)/E) for i in range(E)]
            for pos in range(maxlen)])

        # Second part, apply the cosine to even columns and sin to odds.
        position_enc[:, 0::2] = np.sin(position_enc[:, 0::2])  # dim 2i
        position_enc[:, 1::2] = np.cos(position_enc[:, 1::2])  # dim 2i+1
        position_enc = tf.convert_to_tensor(position_enc, tf.float32) # (maxlen, E)

        # lookup
        outputs = tf.nn.embedding_lookup(position_enc, position_ind)

        # masks
        if masking:
            outputs = tf.where(tf.equal(inputs, 0), inputs, outputs)

        return tf.to_float(outputs)
//  [python]
def positional_encoding(inputs,
                        maxlen,
                        masking=True,
                        scope="positional_encoding"):
    '''Sinusoidal Positional_Encoding. See 3.5
    inputs: 3d tensor. (N, T, E)
    maxlen: scalar. Must be >= T
    masking: Boolean. If True, padding positions are set to zeros.
    scope: Optional scope for `variable_scope`.

    returns
    3d tensor that has the same shape as inputs.
    '''

    E = inputs.get_shape().as_list()[-1] # static
    N, T = tf.shape(inputs)[0], tf.shape(inputs)[1] # dynamic
    with tf.variable_scope(scope, reuse=tf.AUTO_REUSE):
        # position indices
        position_ind = tf.tile(tf.expand_dims(tf.range(T), 0), [N, 1]) # (N, T)

        # First part of the PE function: sin and cos argument
        position_enc = np.array([
            [pos / np.power(10000, (i-i%2)/E) for i in range(E)]
            for pos in range(maxlen)])

        # Second part, apply the cosine to even columns and sin to odds.
        position_enc[:, 0::2] = np.sin(position_enc[:, 0::2])  # dim 2i
        position_enc[:, 1::2] = np.cos(position_enc[:, 1::2])  # dim 2i+1
        position_enc = tf.convert_to_tensor(position_enc, tf.float32) # (maxlen, E)

        # lookup
        outputs = tf.nn.embedding_lookup(position_enc, position_ind)

        # masks
        if masking:
            outputs = tf.where(tf.equal(inputs, 0), inputs, outputs)

        return tf.cast(outputs, tf.float32)
//  [python]
def softmax_summaries(loss, logits, one_hot_labels, name='softmax'):
    """Create the softmax summaries for this cross entropy loss.

  Args:
    loss: Cross-entropy loss.
    logits: The [batch_size, classes] float tensor representing the logits.
    one_hot_labels: The float tensor representing actual class ids. If this is
      [batch_size, classes], then we take the argmax of it first.
    name: Prepended to summary scope.
  """
    tf.summary.scalar(name + '_loss', loss)

    one_hot_labels = tf.cond(
        tf.equal(tf.rank(one_hot_labels), 2),
        lambda: tf.to_int32(tf.argmax(one_hot_labels, 1)),
        lambda: tf.to_int32(one_hot_labels),
    )

    in_top_1 = tf.nn.in_top_k(logits, one_hot_labels, 1)
    tf.summary.scalar(
        name + '_precision@1', tf.reduce_mean(tf.to_float(in_top_1))
    )
    in_top_5 = tf.nn.in_top_k(logits, one_hot_labels, 5)
    tf.summary.scalar(
        name + '_precision@5', tf.reduce_mean(tf.to_float(in_top_5))
    )
//  [python]
def softmax_summaries(loss, logits, one_hot_labels, name='softmax'):
    """Create the softmax summaries for this cross entropy loss.

  Args:
    loss: Cross-entropy loss.
    logits: The [batch_size, classes] float tensor representing the logits.
    one_hot_labels: The float tensor representing actual class ids. If this is
      [batch_size, classes], then we take the argmax of it first.
    name: Prepended to summary scope.
  """
    tf.summary.scalar(name + '_loss', loss)

    one_hot_labels = tf.cond(
        tf.equal(tf.rank(one_hot_labels), 2),
        lambda: tf.cast(tf.argmax(one_hot_labels, 1), tf.int32),
        lambda: tf.cast(one_hot_labels, tf.int32),
    )

    in_top_1 = tf.nn.in_top_k(logits, one_hot_labels, 1)
    tf.summary.scalar(
        name + '_precision@1', tf.reduce_mean(tf.cast(in_top_1, tf.float32))
    )
    in_top_5 = tf.nn.in_top_k(logits, one_hot_labels, 5)
    tf.summary.scalar(
        name + '_precision@5', tf.reduce_mean(tf.cast(in_top_5, tf.float32))
    )
//  [python]
def get_training_targets(
        anchors, groundtruth_boxes,
        positives_threshold=0.5,
        negatives_threshold=0.4):
    """
    Arguments:
        anchors: a float tensor with shape [num_anchors, 4].
        groundtruth_boxes: a float tensor with shape [N, 4].
        positives_threshold: a float number.
        negatives_threshold: a float number.
    Returns:
        regression_targets: a float tensor with shape [num_anchors, 4].
        matches: an int tensor with shape [num_anchors].
    """

    with tf.name_scope('matching'):

        N = tf.shape(groundtruth_boxes)[0]
        num_anchors = tf.shape(anchors)[0]
        only_background = tf.fill([num_anchors], -1)

        matches = tf.to_int32(tf.cond(
            tf.greater(N, 0),
            lambda: match_boxes(
                anchors, groundtruth_boxes,
                positives_threshold=positives_threshold,
                negatives_threshold=negatives_threshold,
                force_match_groundtruth=True
            ),
            lambda: only_background
        ))

    with tf.name_scope('target_creation'):
        regression_targets = create_targets(
            anchors, groundtruth_boxes, matches
        )

    return regression_targets, matches
//  [python]
def get_training_targets(
        anchors, groundtruth_boxes,
        positives_threshold=0.5,
        negatives_threshold=0.4):
    """
    Arguments:
        anchors: a float tensor with shape [num_anchors, 4].
        groundtruth_boxes: a float tensor with shape [N, 4].
        positives_threshold: a float number.
        negatives_threshold: a float number.
    Returns:
        regression_targets: a float tensor with shape [num_anchors, 4].
        matches: an int tensor with shape [num_anchors].
    """

    with tf.name_scope('matching'):

        N = tf.shape(groundtruth_boxes)[0]
        num_anchors = tf.shape(anchors)[0]
        only_background = tf.fill([num_anchors], -1)

        matches = tf.cast(tf.cond(
            tf.greater(N, 0),
            lambda: match_boxes(
                anchors, groundtruth_boxes,
                positives_threshold=positives_threshold,
                negatives_threshold=negatives_threshold,
                force_match_groundtruth=True
            ),
            lambda: only_background
        ), tf.int32)

    with tf.name_scope('target_creation'):
        regression_targets = create_targets(
            anchors, groundtruth_boxes, matches
        )

    return regression_targets, matches
//  [python]
def evaluate(self, out, y):
        correct = tf.equal(tf.argmax(out, axis=1), tf.to_int64(y))
        correct = tf.reduce_mean(tf.cast(correct, tf.float32))
        correct = tf.equal(correct, 1)
        return correct
//  [python]
def evaluate(self, out, y):
        correct = tf.equal(tf.argmax(out, axis=1), tf.cast(y, tf.int64))
        correct = tf.reduce_mean(tf.cast(correct, tf.float32))
        correct = tf.equal(correct, 1)
        return correct
//  [python]
def create_targets(anchors, groundtruth_boxes, matches):
    """Returns regression and classification targets for each anchor.

    Arguments:
        anchors: a float tensor with shape [num_anchors, 4].
        groundtruth_boxes: a float tensor with shape [N, 4].
        matches: an int tensor with shape [num_anchors].
    Returns:
        a float tensor with shape [num_anchors, 4].
    """
    matched_anchor_indices = tf.where(tf.greater_equal(matches, 0))  # shape [num_matches, 1]
    matched_anchor_indices = tf.to_int32(tf.squeeze(matched_anchor_indices, axis=1))

    unmatched_anchor_indices = tf.where(tf.less(matches, 0))  # shape [num_anchors - num_matches, 1]
    unmatched_anchor_indices = tf.to_int32(tf.squeeze(unmatched_anchor_indices, axis=1))

    matched_gt_indices = tf.gather(matches, matched_anchor_indices)  # shape [num_matches]
    matched_gt_boxes = tf.gather(groundtruth_boxes, matched_gt_indices)  # shape [num_matches, 4]
    matched_anchors = tf.gather(anchors, matched_anchor_indices)  # shape [num_matches, 4]

    matched_reg_targets = encode(matched_gt_boxes, matched_anchors)  # shape [num_matches, 4]
    num_unmatched = tf.size(unmatched_anchor_indices)  # num_anchors - num_matches
    unmatched_reg_targets = tf.zeros([num_unmatched, 4], dtype=tf.float32)

    regression_targets = tf.dynamic_stitch(
        [matched_anchor_indices, unmatched_anchor_indices],
        [matched_reg_targets, unmatched_reg_targets]
    )  # shape [num_anchors, 4]

    return regression_targets
//  [python]
def create_targets(anchors, groundtruth_boxes, matches):
    """Returns regression and classification targets for each anchor.

    Arguments:
        anchors: a float tensor with shape [num_anchors, 4].
        groundtruth_boxes: a float tensor with shape [N, 4].
        matches: an int tensor with shape [num_anchors].
    Returns:
        a float tensor with shape [num_anchors, 4].
    """
    matched_anchor_indices = tf.where(tf.greater_equal(matches, 0))  # shape [num_matches, 1]
    matched_anchor_indices = tf.cast(tf.squeeze(matched_anchor_indices, axis=1), tf.int32)

    unmatched_anchor_indices = tf.where(tf.less(matches, 0))  # shape [num_anchors - num_matches, 1]
    unmatched_anchor_indices = tf.cast(tf.squeeze(unmatched_anchor_indices, axis=1), tf.int32)

    matched_gt_indices = tf.gather(matches, matched_anchor_indices)  # shape [num_matches]
    matched_gt_boxes = tf.gather(groundtruth_boxes, matched_gt_indices)  # shape [num_matches, 4]
    matched_anchors = tf.gather(anchors, matched_anchor_indices)  # shape [num_matches, 4]

    matched_reg_targets = encode(matched_gt_boxes, matched_anchors)  # shape [num_matches, 4]
    num_unmatched = tf.size(unmatched_anchor_indices)  # num_anchors - num_matches
    unmatched_reg_targets = tf.zeros([num_unmatched, 4], dtype=tf.float32)

    regression_targets = tf.dynamic_stitch(
        [matched_anchor_indices, unmatched_anchor_indices],
        [matched_reg_targets, unmatched_reg_targets]
    )  # shape [num_anchors, 4]

    return regression_targets
//  [python]
def _create_eval_metric(features, labels, params):
  """Creates eval_metric for model_fn."""
  outputs_to_scales_to_logits = _build_network(
      features, tf_estimator.ModeKeys.EVAL, params)

  semantic_merged_logits = (
      outputs_to_scales_to_logits[common.OUTPUT_TYPE][_MERGED_LOGITS_SCOPE])

  def metric_fn(semantic_merged_logits, labels):
    """Creates metric_fn for TPUEstimatorSpec."""
    logits = tf.image.resize_bilinear(
        semantic_merged_logits, params['crop_size'], align_corners=True)
    predictions_with_shape = tf.argmax(logits, 3, output_type=tf.int32)
    predictions = tf.reshape(predictions_with_shape, shape=[-1])

    labels = tf.reshape(labels, shape=[-1])
    weights = tf.to_float(tf.not_equal(labels, params['ignore_label']))

    # Set ignore_label regions to label 0, because metrics.mean_iou requires
    # range of labels = [0, dataset.num_classes). Note the ignore_lable regions
    # are not evaluated since the corresponding regions contain weights = 0.
    labels = tf.where(
        tf.equal(labels, params['ignore_label']), tf.zeros_like(labels), labels)

    return {
        'miou':
            tf.metrics.mean_iou(
                predictions, labels, params['num_classes'], weights=weights),
    }

  return metric_fn, [semantic_merged_logits, labels]
//  [python]
def _create_eval_metric(features, labels, params):
  """Creates eval_metric for model_fn."""
  outputs_to_scales_to_logits = _build_network(
      features, tf_estimator.ModeKeys.EVAL, params)

  semantic_merged_logits = (
      outputs_to_scales_to_logits[common.OUTPUT_TYPE][_MERGED_LOGITS_SCOPE])

  def metric_fn(semantic_merged_logits, labels):
    """Creates metric_fn for TPUEstimatorSpec."""
    logits = tf.image.resize_bilinear(
        semantic_merged_logits, params['crop_size'], align_corners=True)
    predictions_with_shape = tf.argmax(logits, 3, output_type=tf.int32)
    predictions = tf.reshape(predictions_with_shape, shape=[-1])

    labels = tf.reshape(labels, shape=[-1])
    weights = tf.cast(tf.not_equal(labels, params['ignore_label']), tf.float32)

    # Set ignore_label regions to label 0, because metrics.mean_iou requires
    # range of labels = [0, dataset.num_classes). Note the ignore_lable regions
    # are not evaluated since the corresponding regions contain weights = 0.
    labels = tf.where(
        tf.equal(labels, params['ignore_label']), tf.zeros_like(labels), labels)

    return {
        'miou':
            tf.metrics.mean_iou(
                predictions, labels, params['num_classes'], weights=weights),
    }

  return metric_fn, [semantic_merged_logits, labels]
//  [python]
def inductive_user_embs(self, features, is_training):
        seqs_id = features['seqs_i']

        # positional encoding
        seqs_units = self.item_embs(seqs_id)
        seqs_units = self.pcoding(seqs_units)

        # Dropout
        seqs_units = tf.layers.dropout(seqs_units, rate=self.hidden_dropout_rate,
                                       training=tf.convert_to_tensor(is_training))
        seqs_masks = tf.expand_dims(tf.to_float(tf.not_equal(seqs_id, 0)), -1)

        # Attention
        seqs_outs = seqs_units * seqs_masks
        with tf.variable_scope("TimelyREC/Atttention"):
            seqs_outs = self.attention(layernorm(seqs_outs), seqs_outs, is_training, causality=True)
        with tf.variable_scope("TimelyREC/fforward"):
            seqs_outs = self.fforward(layernorm(seqs_outs), is_training)
        seqs_outs *= seqs_masks

        with tf.variable_scope("TimelyREC/out"):
            seqs_outs = layernorm(seqs_outs)
        return seqs_outs
//  [python]
def inductive_user_embs(self, features, is_training):
        seqs_id = features['seqs_i']

        # positional encoding
        seqs_units = self.item_embs(seqs_id)
        seqs_units = self.pcoding(seqs_units)

        # Dropout
        seqs_units = tf.layers.dropout(seqs_units, rate=self.hidden_dropout_rate,
                                       training=tf.convert_to_tensor(is_training))
        seqs_masks = tf.expand_dims(tf.cast(tf.not_equal(seqs_id, 0), tf.float32), -1)

        # Attention
        seqs_outs = seqs_units * seqs_masks
        with tf.variable_scope("TimelyREC/Atttention"):
            seqs_outs = self.attention(layernorm(seqs_outs), seqs_outs, is_training, causality=True)
        with tf.variable_scope("TimelyREC/fforward"):
            seqs_outs = self.fforward(layernorm(seqs_outs), is_training)
        seqs_outs *= seqs_masks

        with tf.variable_scope("TimelyREC/out"):
            seqs_outs = layernorm(seqs_outs)
        return seqs_outs
//  [python]
def keypoits_rotate(keypoints,angle,width,height):
    r_angle = -angle * 3.1415926 / 180
    cos = tf.cos(r_angle)
    sin = tf.sin(r_angle)
    m = tf.stack([cos, -sin, sin, cos])
    m = tf.reshape(m,[2,2])
    old_shape = btf.combined_static_and_dynamic_shape(keypoints)
    keypoints = tf.reshape(keypoints,[-1,2])
    org_x,org_y = tf.unstack(keypoints,axis=-1)
    width = tf.to_float(width)
    height = tf.to_float(height)
    keypoints = keypoints-tf.convert_to_tensor([[(width-1)/2,(height-1)/2]])
    keypoints = tf.matmul(m,keypoints,transpose_b=True)
    keypoints = tf.transpose(keypoints,[1,0])+tf.convert_to_tensor([[(width-1)/2,(height-1)/2]])
    x,y = tf.unstack(keypoints,axis=-1)

    cond = tf.logical_and(org_x>=0,org_y>=0)
    x = tf.where(cond,x,org_x)
    y = tf.where(cond,y,org_y)

    cond = tf.logical_and(tf.logical_and(x>=0,x<width), tf.logical_and(y>=0,y<height))
    x = tf.where(cond,x,tf.ones_like(x)*-100)
    y = tf.where(cond,y,tf.ones_like(y)*-100)

    keypoints = tf.stack([x,y],axis=-1)
    keypoints = tf.reshape(keypoints,old_shape)
    return keypoints
//  [python]
def keypoits_rotate(keypoints,angle,width,height):
    r_angle = -angle * 3.1415926 / 180
    cos = tf.cos(r_angle)
    sin = tf.sin(r_angle)
    m = tf.stack([cos, -sin, sin, cos])
    m = tf.reshape(m,[2,2])
    old_shape = btf.combined_static_and_dynamic_shape(keypoints)
    keypoints = tf.reshape(keypoints,[-1,2])
    org_x,org_y = tf.unstack(keypoints,axis=-1)
    width = tf.cast(width,tf.float32)
    height = tf.cast(height,tf.float32)
    keypoints = keypoints-tf.convert_to_tensor([[(width-1)/2,(height-1)/2]])
    keypoints = tf.matmul(m,keypoints,transpose_b=True)
    keypoints = tf.transpose(keypoints,[1,0])+tf.convert_to_tensor([[(width-1)/2,(height-1)/2]])
    x,y = tf.unstack(keypoints,axis=-1)

    cond = tf.logical_and(org_x>=0,org_y>=0)
    x = tf.where(cond,x,org_x)
    y = tf.where(cond,y,org_y)

    cond = tf.logical_and(tf.logical_and(x>=0,x<width), tf.logical_and(y>=0,y<height))
    x = tf.where(cond,x,tf.ones_like(x)*-100)
    y = tf.where(cond,y,tf.ones_like(y)*-100)

    keypoints = tf.stack([x,y],axis=-1)
    keypoints = tf.reshape(keypoints,old_shape)
    return keypoints
//  [python]
def file_based_input_fn_builder(input_file, seq_length, is_training,
                                drop_remainder, num_choices):
  """Creates an `input_fn` closure to be passed to TPUEstimator."""

  input_file = input_file.split(",")

  expanded_files = []
  for infile in input_file:
    try:
      sharded_files = tf.io.gfile.glob(infile)
      expanded_files.append(sharded_files)
    except tf.errors.OpError:
      expanded_files.append(infile)

  name_to_features = {}
  for i in range(num_choices):
    name_to_features["input_ids" + str(i)] = tf.FixedLenFeature([seq_length],
                                                                tf.int64)
    name_to_features["input_mask" + str(i)] = tf.FixedLenFeature([seq_length],
                                                                 tf.int64)
    name_to_features["segment_ids" + str(i)] = tf.FixedLenFeature([seq_length],
                                                                  tf.int64)
  name_to_features["label_types"] = tf.FixedLenFeature([8], tf.int64)
  name_to_features["labels"] = tf.FixedLenFeature([8], tf.int64)

  def _decode_record(record, name_to_features):
    """Decodes a record to a TensorFlow example."""
    example = tf.parse_single_example(record, name_to_features)

    # tf.Example only supports tf.int64, but the TPU only supports tf.int32.
    # So cast all int64 to int32.
    for name in list(example.keys()):
      t = example[name]
      if t.dtype == tf.int64:
        t = tf.to_int32(t)
      example[name] = t

    return example

  def input_fn(params):
    """The actual input function."""
    batch_size = params["batch_size"]

    if len(expanded_files) == 1:
      d = tf.data.TFRecordDataset(expanded_files[0])
      if is_training:
        d = d.repeat()
        d = d.shuffle(buffer_size=256)
    else:
      dataset_list = [
          tf.data.TFRecordDataset(expanded_files[i])
          for i in range(len(expanded_files))
      ]
      if is_training:
        dataset_list = [
            d.repeat() for d in dataset_list
        ]
      # Note that an alternative is to load from the list directly without
      # specifying a range. Sample below:
      # d = tf.data.experimental.sample_from_datasets(dataset_list)
      choice_dataset = tf.data.Dataset.range(len(dataset_list)).repeat()

      d = tf.data.experimental.choose_from_datasets(dataset_list,
                                                    choice_dataset)
      if is_training:
        d = d.shuffle(buffer_size=256)

    d = d.apply(
        tf.data.experimental.map_and_batch(
            lambda record: _decode_record(record, name_to_features),
            batch_size=batch_size,
            drop_remainder=drop_remainder))

    return d

  return input_fn
//  [python]
def file_based_input_fn_builder(input_file, seq_length, is_training,
                                drop_remainder, num_choices):
  """Creates an `input_fn` closure to be passed to TPUEstimator."""

  input_file = input_file.split(",")

  expanded_files = []
  for infile in input_file:
    try:
      sharded_files = tf.io.gfile.glob(infile)
      expanded_files.append(sharded_files)
    except tf.errors.OpError:
      expanded_files.append(infile)

  name_to_features = {}
  for i in range(num_choices):
    name_to_features["input_ids" + str(i)] = tf.FixedLenFeature([seq_length],
                                                                tf.int64)
    name_to_features["input_mask" + str(i)] = tf.FixedLenFeature([seq_length],
                                                                 tf.int64)
    name_to_features["segment_ids" + str(i)] = tf.FixedLenFeature([seq_length],
                                                                  tf.int64)
  name_to_features["label_types"] = tf.FixedLenFeature([8], tf.int64)
  name_to_features["labels"] = tf.FixedLenFeature([8], tf.int64)

  def _decode_record(record, name_to_features):
    """Decodes a record to a TensorFlow example."""
    example = tf.parse_single_example(record, name_to_features)

    # tf.Example only supports tf.int64, but the TPU only supports tf.int32.
    # So cast all int64 to int32.
    for name in list(example.keys()):
      t = example[name]
      if t.dtype == tf.int64:
        t = tf.cast(t, tf.int32)
      example[name] = t

    return example

  def input_fn(params):
    """The actual input function."""
    batch_size = params["batch_size"]

    if len(expanded_files) == 1:
      d = tf.data.TFRecordDataset(expanded_files[0])
      if is_training:
        d = d.repeat()
        d = d.shuffle(buffer_size=256)
    else:
      dataset_list = [
          tf.data.TFRecordDataset(expanded_files[i])
          for i in range(len(expanded_files))
      ]
      if is_training:
        dataset_list = [
            d.repeat() for d in dataset_list
        ]
      # Note that an alternative is to load from the list directly without
      # specifying a range. Sample below:
      # d = tf.data.experimental.sample_from_datasets(dataset_list)
      choice_dataset = tf.data.Dataset.range(len(dataset_list)).repeat()

      d = tf.data.experimental.choose_from_datasets(dataset_list,
                                                    choice_dataset)
      if is_training:
        d = d.shuffle(buffer_size=256)

    d = d.apply(
        tf.data.experimental.map_and_batch(
            lambda record: _decode_record(record, name_to_features),
            batch_size=batch_size,
            drop_remainder=drop_remainder))

    return d

  return input_fn
//  [python]
def clip_boxes(boxes, image_shape, name=None):
  # boxes [K, 4] or [B, K, 4]
  boxes = tf.maximum(boxes, 0.0) # lower bound
  # image_shape is HW,
  # HW -> [W, H, W, H] # <- box
  m = tf.tile(tf.reverse(image_shape, [0]), [2]) # of shape ()
  boxes = tf.minimum(boxes, tf.to_float(m), name=name) # upper bound
  return boxes
//  [python]
def clip_boxes(boxes, image_shape, name=None):
  # boxes [K, 4] or [B, K, 4]
  boxes = tf.maximum(boxes, 0.0) # lower bound
  # image_shape is HW,
  # HW -> [W, H, W, H] # <- box
  m = tf.tile(tf.reverse(image_shape, [0]), [2]) # of shape ()
  boxes = tf.minimum(boxes, tf.cast(m, tf.float32), name=name) # upper bound
  return boxes
//  [python]
def crop_and_resize_nhwc(image, boxes, box_ind, crop_size):
  # image feature [1,FS,FS,C]
  # boxes [N,4]
  # box_ind [N] all zero?
  # return [N,crop_size,crop_size,C]
  def transform_fpcoor_for_tf(boxes, image_shape, crop_shape):

    x0, y0, x1, y1 = tf.split(boxes, 4, axis=1)

    spacing_w = (x1 - x0) / tf.to_float(crop_shape[1])
    spacing_h = (y1 - y0) / tf.to_float(crop_shape[0])

    nx0 = (x0 + spacing_w / 2 - 0.5) / tf.to_float(image_shape[1] - 1)
    ny0 = (y0 + spacing_h / 2 - 0.5) / tf.to_float(image_shape[0] - 1)

    nw = spacing_w * tf.to_float(crop_shape[1] - 1) / \
        tf.to_float(image_shape[1] - 1)
    nh = spacing_h * tf.to_float(crop_shape[0] - 1) / \
        tf.to_float(image_shape[0] - 1)

    return tf.concat([ny0, nx0, ny0 + nh, nx0 + nw], axis=1)

  image_shape = tf.shape(image)[1:3]
  boxes = transform_fpcoor_for_tf(boxes, image_shape, [crop_size, crop_size])
  ret = tf.image.crop_and_resize(
      image, boxes, box_ind,
      crop_size=[crop_size, crop_size])
  return ret
//  [python]
def crop_and_resize_nhwc(image, boxes, box_ind, crop_size):
  # image feature [1,FS,FS,C]
  # boxes [N,4]
  # box_ind [N] all zero?
  # return [N,crop_size,crop_size,C]
  def transform_fpcoor_for_tf(boxes, image_shape, crop_shape):

    x0, y0, x1, y1 = tf.split(boxes, 4, axis=1)

    spacing_w = (x1 - x0) / tf.cast(crop_shape[1], tf.float32)
    spacing_h = (y1 - y0) / tf.cast(crop_shape[0], tf.float32)

    nx0 = (x0 + spacing_w / 2 - 0.5) / tf.cast(image_shape[1] - 1, tf.float32)
    ny0 = (y0 + spacing_h / 2 - 0.5) / tf.cast(image_shape[0] - 1, tf.float32)

    nw = spacing_w * tf.cast(crop_shape[1] - 1, tf.float32) / \
        tf.cast(image_shape[1] - 1, tf.float32)
    nh = spacing_h * tf.cast(crop_shape[0] - 1, tf.float32) / \
        tf.cast(image_shape[0] - 1, tf.float32)

    return tf.concat([ny0, nx0, ny0 + nh, nx0 + nw], axis=1)

  image_shape = tf.shape(image)[1:3]
  boxes = transform_fpcoor_for_tf(boxes, image_shape, [crop_size, crop_size])
  ret = tf.image.crop_and_resize(
      image, boxes, box_ind,
      crop_size=[crop_size, crop_size])
  return ret
//  [python]
def _secondary_accuracy(config, dssps, targets, masks, group_filter):
    """ Computes (non-differentiable) accuracy of predicted secondary 
        structures based on targets. """

    # XXX THIS SECTION IS NOT CURRENTLY FUNCTIONAL

    # pick top classes
    tops = tf.to_int32(tf.argmax(dssps, 2)) # [NUM_STEPS, BATCH_SIZE]

    # compute matches, cast, and reduce to counts of matches
    eff_num_stepss = effective_steps(masks, config['num_edge_residues'])         # [BATCH_SIZE]
    matches = tf.to_float(tf.equal(tops, targets))                               # [NUM_STEPS, BATCH_SIZE]
    matches_reduced = tf.reduce_sum(matches, 0)                                  # [BATCH_SIZE]
    matches_normalized = tf.div(matches_reduced, eff_num_stepss, name='matches') # [BATCH_SIZE]

    # reduce accuracy based on normalization behavior
    accuracy = _reduce_loss(matches_normalized, masks, group_filter, 
                            config['secondary_normalization'], config['num_edge_residues'], name='secondary_accuracy')

    # add to relevant collections for summaries, etc.
    if config['log_model_summaries']: 
        tf.add_to_collection(config['name'] + '_matchess',             matches_normalized) # never filters by group
        tf.add_to_collection(config['name'] + '_secondary_accuracies', accuracy)

    return accuracy
//  [python]
def _secondary_accuracy(config, dssps, targets, masks, group_filter):
    """ Computes (non-differentiable) accuracy of predicted secondary 
        structures based on targets. """

    # XXX THIS SECTION IS NOT CURRENTLY FUNCTIONAL

    # pick top classes
    tops = tf.cast(tf.argmax(dssps, 2), tf.int32) # [NUM_STEPS, BATCH_SIZE]

    # compute matches, cast, and reduce to counts of matches
    eff_num_stepss = effective_steps(masks, config['num_edge_residues'])         # [BATCH_SIZE]
    matches = tf.cast(tf.equal(tops, targets), tf.float32)                               # [NUM_STEPS, BATCH_SIZE]
    matches_reduced = tf.reduce_sum(matches, 0)                                  # [BATCH_SIZE]
    matches_normalized = tf.div(matches_reduced, eff_num_stepss, name='matches') # [BATCH_SIZE]

    # reduce accuracy based on normalization behavior
    accuracy = _reduce_loss(matches_normalized, masks, group_filter, 
                            config['secondary_normalization'], config['num_edge_residues'], name='secondary_accuracy')

    # add to relevant collections for summaries, etc.
    if config['log_model_summaries']: 
        tf.add_to_collection(config['name'] + '_matchess',             matches_normalized) # never filters by group
        tf.add_to_collection(config['name'] + '_secondary_accuracies', accuracy)

    return accuracy
//  [python]
def crop_and_resize(image, boxes, box_ind, crop_size, pad_border=False):
  # image feature [1,C,FS,FS] # for mask gt [N_FG, 1, H, W]
  # boxes [N,4]
  # box_ind [N] all zero?

  if pad_border:
    image = tf.pad(image, [[0, 0], [0, 0], [1, 1], [1, 1]], mode="SYMMETRIC")
    boxes = boxes + 1

  # return [N,C,crop_size,crop_size]
  def transform_fpcoor_for_tf(boxes, image_shape, crop_shape):
    """
    The way tf.image.crop_and_resize works (with normalized box):
    Initial point (the value of output[0]): x0_box * (W_img - 1)
    Spacing: w_box * (W_img - 1) / (W_crop - 1)
    Use the above grid to bilinear sample.

    However, what we want is (with fpcoor box):
    Spacing: w_box / W_crop
    Initial point: x0_box + spacing/2 - 0.5
    (-0.5 because bilinear sample assumes floating point coordinate (0.0, 0.0)
    is the same as pixel value (0, 0))

    This function transform fpcoor boxes to a format to be used by
    tf.image.crop_and_resize

    Returns:
      y1x1y2x2
    """
    x0, y0, x1, y1 = tf.split(boxes, 4, axis=1)

    spacing_w = (x1 - x0) / tf.to_float(crop_shape[1])
    spacing_h = (y1 - y0) / tf.to_float(crop_shape[0])

    nx0 = (x0 + spacing_w / 2 - 0.5) / tf.to_float(image_shape[1] - 1)
    ny0 = (y0 + spacing_h / 2 - 0.5) / tf.to_float(image_shape[0] - 1)

    nw = spacing_w * tf.to_float(crop_shape[1] - 1) / \
        tf.to_float(image_shape[1] - 1)
    nh = spacing_h * tf.to_float(crop_shape[0] - 1) / \
        tf.to_float(image_shape[0] - 1)

    return tf.concat([ny0, nx0, ny0 + nh, nx0 + nw], axis=1)

  image_shape = tf.shape(image)[2:]
  boxes = transform_fpcoor_for_tf(boxes, image_shape, [crop_size, crop_size])
  image = tf.transpose(image, [0, 2, 3, 1])   # 1hwc
  ret = tf.image.crop_and_resize(
      image, boxes, box_ind,
      crop_size=[crop_size, crop_size])
  ret = tf.transpose(ret, [0, 3, 1, 2])   # Ncss
  return ret