【问题标题】:Jaccard's distance matrix with tensorflow带有张量流的 Jaccard 距离矩阵
【发布时间】:2017-06-23 04:56:42
【问题描述】:

我想使用Jaccard 距离计算距离矩阵。并尽可能快地这样做。我曾经使用scikit-learn's pairwise_distances 函数。但 scikit-learn 不打算支持 GPU,甚至还有一个 known bug 让函数在并行运行时变慢。

我唯一的限制是生成的距离矩阵然后可以输入到scikit-learn's DBSCAN 聚类算法。我正在考虑使用 tensorflow 实现计算,但找不到一个好的简单方法。


PS:我有理由预先计算距离矩阵,而不是让 DBSCAN 根据需要进行计算。

【问题讨论】:

    标签: python tensorflow distance


    【解决方案1】:

    嘿,我也遇到了同样的问题。

    鉴于 Jaccard 相似度是真阳性 (tp) 与真阳性、假阴性 (fn) 和假阳性 (fp) 之和的比率,我想出了这个解决方案:

        def jaccard_distance(self):
            tp = tf.reduce_sum(tf.mul(self.target, self.prediction), 1)
            fn = tf.reduce_sum(tf.mul(self.target, 1-self.prediction), 1)
            fp = tf.reduce_sum(tf.mul(1-self.target, self.prediction), 1)
            return 1 - (tp / (tp + fn + fp))
    

    希望这会有所帮助!

    【讨论】:

    • 您有 3 个矩阵乘法,这可能对性能不利。
    【解决方案2】:

    我不是 tensorflow 专家,但这是我得到的解决方案。据我所知,张量流中对列表的所有对进行计算的唯一方法是进行矩阵乘法或使用广播规则,该解决方案在某些时候同时使用两者。

    假设我们有一个输入布尔矩阵,其中n_samples 行,每组一个,n_features 列,每个可能元素一个。第 i 行第 j 列中的值 True 表示第 i 集合包含元素 j 。就像scikit-learn's pairwise_distances 期望一样。然后我们可以按照以下步骤进行。

    1. 将矩阵转换为数字,True 为 1,False 为 0。
    2. 将矩阵乘以它自己的转置。这会产生一个矩阵,其中每个元素 M[i][j] 包含第 i 和第 j 集之间的交集的大小。
    3. 通过按行对输入矩阵求和,计算包含所有集合的基数的 cardv 向量。
    4. 根据cardv 制作行向量和列向量。
    5. 计算1 - M / (cardvrow + cardvcol - M)。添加行向量和列向量时,广播规则将完成所有工作。

    这个算法整体上看起来有点 hack-ish,但它的工作原理和产生的结果在 scikit-learn 的 pairwise_distances 函数计算的结果的合理范围内。更好的算法可能应该对每对输入向量进行一次传递,并且只计算矩阵的一半,因为它是对称的。欢迎任何改进。

    setsin = tf.placeholder(tf.bool, shape=(N, M))
    sets = tf.cast(setsin, tf.float16)
    mat = tf.matmul(sets, sets, transpose_b=True, name="Main_matmul")
    #mat = tf.cast(mat, tf.float32, name="Upgrade_mat")
    #sets = tf.cast(sets, tf.float32, name="Upgrade_sets")
    cardinal = tf.reduce_sum(sets, 1, name="Richelieu")
    cardinalrow = tf.expand_dims(cardinal, 0)
    cardinalcol = tf.expand_dims(cardinal, 1)
    
    mat = 1 - mat / (cardinalrow + cardinalcol - mat)
    

    我使用了float16 类型,因为它似乎比float32 快得多。转换为 float32 可能仅在基数大到足以使它们不准确或在执行除法时需要更高精度时才有用。但即使需要强制转换,将矩阵乘法作为float16 似乎仍然相关。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2017-04-13
      • 2023-03-07
      • 1970-01-01
      • 2016-03-11
      • 2019-09-04
      • 2018-05-24
      • 2016-12-06
      • 2011-08-08
      相关资源
      最近更新 更多