tenorflow: как выполнить поэлементное умножение между двумя разреженными матрицами

У меня есть две разреженные матрицы, объявленные с использованием tf.sparse_placeholder. Мне нужно выполнить поэлементное умножение между двумя матрицами. Но я не могу найти такую ​​реализацию в tensorflow. Наиболее связанная функция - tf.sparse_tensor_dense_matmul, но это функция, выполняющая матричное умножение между одной разреженной матрицей и одной плотной матрицей.

Я надеюсь найти выполнение поэлементного умножения двух разреженных матриц. Есть ли реализация этого в tensorflow?

Я показываю следующий пример выполнения умножения между плотными матрицами. Я с нетерпением жду решения.

import tensorflow as tf
import numpy as np

# Element-wise multiplication, two dense matrices
A = tf.placeholder(tf.float32, shape=(100, 100))
B = tf.placeholder(tf.float32, shape=(100, 100))
C = tf.multiply(A, B)
sess = tf.InteractiveSession()
RandA = np.random.rand(100, 100)
RandB = np.random.rand(100, 100)
print sess.run(C, feed_dict={A: RandA, B: RandB})

# matrix multiplication, A is sparse and B is dense
A = tf.sparse_placeholder(tf.float32)
B = tf.placeholder(tf.float32, shape=(5,5))
C = tf.sparse_tensor_dense_matmul(A, B)
sess = tf.InteractiveSession()
indices = np.array([[3, 2], [1, 2]], dtype=np.int64)
values = np.array([1.0, 2.0], dtype=np.float32)
shape = np.array([5,5], dtype=np.int64)
Sparse_A = tf.SparseTensorValue(indices, values, shape)
RandB = np.ones((5, 5))
print sess.run(C, feed_dict={A: Sparse_A, B: RandB})

Большое тебе спасибо!!!


person pfc    schedule 17.08.2017    source источник
comment
У меня недостаточно комментариев для комментариев, но это выглядит многообещающим: stackoverflow.com/questions/44810168/   -  person Kevinj22    schedule 20.11.2017


Ответы (4)


В настоящее время в TensorFlow нет операции поэлементного умножения с разреженным и разреженным фрагментами.

В настоящее время мы не планируем добавлять поддержку для этого, но мы определенно приветствуем участие! Не стесняйтесь создавать здесь проблему с github: https://github.com/tensorflow/tensorflow/issues/new и, возможно, вы или кто-то из сообщества сможете его подобрать :)

Спасибо!

person suharshs    schedule 24.08.2017
comment
Спасибо. Хотя и не рад это знать. - person pfc; 24.09.2017
comment
Тем не менее, создайте проблему, так как кто-то может ее подхватить. Просто никто из команды активно этим не занимается. Спасибо! - person suharshs; 26.09.2017

вы можете использовать tf.matmul или _ 2_ также для разреженных матриц; установив a_is_sparse и b_is_sparse как True.

matmul(
    a,
    b,
    transpose_a=False,
    transpose_b=False,
    adjoint_a=False,
    adjoint_b=False,
    a_is_sparse=False,
    b_is_sparse=False,
    name=None
)

Для поэлементного умножения одним решением является использование tf.sparse_to_dense для преобразования разреженного тензора для плотного представления и использования tf.multiply для поэлементного умножения

person Ishant Mrinal    schedule 17.08.2017
comment
Спасибо. Это матричное умножение или поэлементное умножение? Мне нужно поэлементное умножение. - person pfc; 17.08.2017
comment
это матричное умножение, а не поэлементное; также tf.sparse_tensor_dense_matmul не является поэлементным. - person Ishant Mrinal; 17.08.2017
comment
OK. Тогда подождем других решений. - person pfc; 17.08.2017

Решение из другого сообщения работает.

https://stackoverflow.com/a/45103767/2415428

Используйте __mul__ для поэлементного умножения.

Ссылка TF2.1: https://www.tensorflow.org/api_docs / python / tf / sparse / SparseTensor # mul

person Kimmi    schedule 25.02.2020

Я использую Tensorflow 2.4.1.

Вот мой способ поэлементного умножения двух разреженных тензоров:

def sparse_element_wise_mul(a: tf.SparseTensor, b: tf.SparseTensor):
    a_plus_b = tf.sparse.add(a, b)
    a_plus_b_square = tf.square(a_plus_b)
    minus_a_square = tf.negative(tf.square(a))
    minus_b_square = tf.negative(tf.square(b))
    _2ab = tf.sparse.add(
        tf.sparse.add(
            a_plus_b_square,
            minus_a_square
        ),
        minus_b_square
    )
    ab = tf.sparse.map_values(tf.multiply, _2ab, 0.5)
    return ab

Вот простое объяснение:

Учитывая, что

(a+b)^2 = a^2 + 2a*b + b^2

мы можем вычислить a * b по

a*b = ((a+b)^2 - a^2 - b^2) / 2

Кажется, что градиент можно правильно рассчитать с помощью такого обходного пути.

person Boyo Chen    schedule 29.05.2021