code: def similarity_matrix(self, x_subjects=None, y_subjects=None, symmetric=False):
          
          if x_subjects is None:
              x_subjects = []
          if y_subjects is None:
              y_subjects = []
  
          xset = set(x_subjects)
          yset = set(y_subjects)
          zset = xset.union(yset)
  
          # first built map of gene->termClosure.
          # this could be calculated ahead of time for all g,
          # but this may be space-expensive. TODO: benchmark
          gmap={}
          for z in zset:
              gmap[z] = self.inferred_types(z)
          ilist = []
          for x in x_subjects:
              for y in y_subjects:
                  if not symmetric or x<y:
                      shared = gmap[x].intersection(gmap[y])
                      union = gmap[x].union(gmap[y])
                      j = 0
                      if len(union)>0:
                          j = len(shared) / len(union)
                      ilist.append({'x':x,'y':y,'shared':shared, 'c':len(shared), 'j':j})
          return self.intersectionlist_to_matrix(ilist, x_subjects, y_subjects)
docs: Query for similarity matrix between groups of subjects
  
          Return a list of intersection result objects with keys:
           - x : term from x
           - y : term from y
           - c : count of intersection
           - j : jaccard score