old_contents: import numpy as np
  
  
  def accuracy(output, target, topk=(1,)):
      """Computes the precision@k for the specified values of k"""
      maxk = max(topk)
      batch_size = target.size(0)
  
      _, pred = output.topk(maxk, 1, True, True)
      pred = pred.t()
      correct = pred.eq(target.view(1, -1).expand_as(pred))
  
      ret = []
      for k in topk:
          correct_k = correct[:k].view(-1).float().sum(0)
          ret.append(correct_k.mul_(1. / batch_size))
      return ret
  
  
  def cmc(distmat, query_ids=None, gallery_ids=None,
          query_cams=None, gallery_cams=None, topk=100):
      m, n = distmat.shape
      if query_ids is None:
          query_ids = np.arange(m)
      if gallery_ids is None:
          gallery_ids = np.arange(n)
      if query_cams is None:
          query_cams = np.zeros(m).astype(np.int32)
      if gallery_cams is None:
          gallery_cams = np.ones(m).astype(np.int32)
      query_ids = np.asarray(query_ids)
      gallery_ids = np.asarray(gallery_ids)
      query_cams = np.asarray(query_cams)
      gallery_cams = np.asarray(gallery_cams)
      indices = np.argsort(distmat, axis=1)
      matches = (gallery_ids[indices] == query_ids[:, np.newaxis])
      ret = np.zeros(topk)
      num_valid_queries = 0
      for i in range(m):
          valid = (gallery_ids != query_ids[i]) | (gallery_cams != query_cams[i])
          index = np.nonzero(matches[i, valid])[0]
          if len(index) == 0: continue
          delta = 1. / len(index)
          for j, k in enumerate(index):
              ret[k - j] += delta
          num_valid_queries += 1
      if num_valid_queries == 0:
          raise RuntimeError("No valid query")
      return ret.cumsum() / num_valid_queries
  
new_contents: import numpy as np
  
  
  def accuracy(output, target, topk=(1,)):
      """Computes the precision@k for the specified values of k"""
      maxk = max(topk)
      batch_size = target.size(0)
  
      _, pred = output.topk(maxk, 1, True, True)
      pred = pred.t()
      correct = pred.eq(target.view(1, -1).expand_as(pred))
  
      ret = []
      for k in topk:
          correct_k = correct[:k].view(-1).float().sum(0)
          ret.append(correct_k.mul_(1. / batch_size))
      return ret
  
  
  def cmc(distmat, query_ids=None, gallery_ids=None,
          query_cams=None, gallery_cams=None, topk=100):
      m, n = distmat.shape
      if query_ids is None:
          query_ids = np.arange(m)
      if gallery_ids is None:
          gallery_ids = np.arange(n)
      if query_cams is None:
          query_cams = np.zeros(m).astype(np.int32)
      if gallery_cams is None:
          gallery_cams = np.ones(m).astype(np.int32)
      query_ids = np.asarray(query_ids)
      gallery_ids = np.asarray(gallery_ids)
      query_cams = np.asarray(query_cams)
      gallery_cams = np.asarray(gallery_cams)
      indices = np.argsort(distmat, axis=1)
      matches = (gallery_ids[indices] == query_ids[:, np.newaxis])
      ret = np.zeros(topk)
      num_valid_queries = 0
      for i in range(m):
          valid = ((gallery_ids[indices[i]] != query_ids[i]) |
                   (gallery_cams[indices[i]] != query_cams[i]))
          index = np.nonzero(matches[i, valid])[0]
          if len(index) == 0: continue
          delta = 1. / len(index)
          for j, k in enumerate(index):
              if k - j >= topk: break
              ret[k - j] += delta
          num_valid_queries += 1
      if num_valid_queries == 0:
          raise RuntimeError("No valid query")
      return ret.cumsum() / num_valid_queries
  
subject: Fix a bug in CMC