Tensorflow一个热门编码器?

tensorflow是否有类似scikit学习处理分类数据的一个热门编码器 ? 将使用tf.string的占位符行为作为分类数据?

我意识到我可以在将数据发送到tensorflow之前手动预处理数据,但是内置它非常方便。

从TensorFlow 0.8开始,现在有一个本地的一个热门操作, tf.one_hot可以将一组稀疏标签转换为一个密集的单热表示。 除了tf.nn.sparse_softmax_cross_entropy_with_logits ,在某些情况下,您可以直接在稀疏标签上计算交叉熵,而不是将它们转换为one-hot。

以前的回答,如果你想以旧的方式来做: @萨尔瓦多的答案是正确的 – 那里(曾经是)没有本地操作做到这一点。 尽pipe如此,您可以使用稀疏到密集的运算符在tensorflow中本地执行:

 num_labels = 10 # label_batch is a tensor of numeric labels to process # 0 <= label < num_labels sparse_labels = tf.reshape(label_batch, [-1, 1]) derived_size = tf.shape(label_batch)[0] indices = tf.reshape(tf.range(0, derived_size, 1), [-1, 1]) concated = tf.concat(1, [indices, sparse_labels]) outshape = tf.pack([derived_size, num_labels]) labels = tf.sparse_to_dense(concated, outshape, 1.0, 0.0) 

输出标签是batch_size x num_labels的一个热点matrix。

还请注意,截至tf.nn.sparse_softmax_cross_entropy_with_logits日(我认为最终将成为0.7版本的一部分),TensorFlow也有tf.nn.sparse_softmax_cross_entropy_with_logits操作,在某些情况下可以让您进行训练而无需转换为单热编码。

编辑添加:最后,您可能需要明确设置标签的形状。 形状推断不能识别num_labels组件的大小。 如果您不需要带有derived_size的dynamic批处理大小,则可以简化。

编辑2016-02-12更改下面的每条评论outshape的任务。

tf.one_hot()在TF中可用并且易于使用。

假设你有4个可能的类别(猫,狗,鸟,人类)和2个实例(猫,人类)。 所以你的depth=4 ,你的indices=[0, 3]

 import tensorflow as tf res = tf.one_hot(indices=[0, 3], depth=4) with tf.Session() as sess: print sess.run(res) 

请记住,如果您提供索引= -1,您将在您的一个热点向量中获得全零。

旧的答案,当这个function不可用。

通过python文档查看后,我还没有发现任何类似的东西。 有一件事增强了我不相信的信念,就是在他们自己的例子中,他们手工写了一个one_hot

 def dense_to_one_hot(labels_dense, num_classes=10): """Convert class labels from scalars to one-hot vectors.""" num_labels = labels_dense.shape[0] index_offset = numpy.arange(num_labels) * num_classes labels_one_hot = numpy.zeros((num_labels, num_classes)) labels_one_hot.flat[index_offset + labels_dense.ravel()] = 1 return labels_one_hot 

你也可以在scikitlearn中做到这一点 。

numpy做到了!

 import numpy as np np.eye(n_labels)[target_vector] 

最近版本的TensorFlow(nightlies,甚至0.7.1)有一个叫做tf.one_hot的操作,可以做你想做的事情。 一探究竟!

另一方面,如果你有一个密集的matrix,你想查找和聚合它的值,你会想使用embedding_lookup函数。

对一个整数或整数列表进行单热编码的简单方法:

 a = 5 b = [1, 2, 3] # one hot an integer one_hot_a = tf.nn.embedding_lookup(np.identity(10), a) # one hot a list of integers one_hot_b = tf.nn.embedding_lookup(np.identity(max(b)+1), b) 

也许是由于2015年11月以来Tensorflow的变化,但是@dga的答案产生了错误。 我确实得到它与以下修改工作:

 sparse_labels = tf.reshape(label_batch, [-1, 1]) derived_size = tf.shape(sparse_labels)[0] indices = tf.reshape(tf.range(0, derived_size, 1), [-1, 1]) concated = tf.concat(1, [indices, sparse_labels]) outshape = tf.concat(0, [tf.reshape(derived_size, [1]), tf.reshape(num_labels, [1])]) labels = tf.sparse_to_dense(concated, outshape, 1.0, 0.0) 

看看tf.nn.embedding_lookup 。 它从分类ID映射到embedded。

有关如何将其用于input数据的示例,请参阅此处 。

你可以使用tf.sparse_to_dense :

sparse_indices参数表示应该去哪里,output_shape应该被设置为可能的输出的数量(例如标签的数量),并且sparse_values应该是1与期望的types(它将决定输出types的typessparse_values)。

张量stream的当前版本实现以下用于创build单张张量的函数:

https://www.tensorflow.org/versions/master/api_docs/python/array_ops.html#one_hot

Scikit Flow中有embedding_ops和处理分类variables的例子等。

如果你刚开始学习TensorFlow,我build议你先在TensorFlow / skflow中尝试一下例子 ,然后一旦你更熟悉TensorFlow,那么插入TensorFlow代码来构build你想要的自定义模型是相当容易的也是这个例子)。

希望这些图片和文字理解的例子可以让你开始,让我们知道如果你遇到任何问题! (在SO中发布问题或标记skflow)。

有几个方法可以做到这一点。

 ans = tf.constant([[5, 6, 0, 0], [5, 6, 7, 0]]) #batch_size*max_seq_len labels = tf.reduce_sum(tf.nn.embedding_lookup(np.identity(10), ans), 1) >>> [[ 0. 0. 0. 0. 0. 1. 1. 0. 0. 0.] >>> [ 0. 0. 0. 0. 0. 1. 1. 1. 0. 0.]] 

另一种方法是。

 labels2 = tf.reduce_sum(tf.one_hot(ans, depth=10, on_value=1, off_value=0, axis=1), 2) >>> [[0 0 0 0 0 1 1 0 0 0] >>> [0 0 0 0 0 1 1 1 0 0]] 

我的@CFB版本和@dga例子缩短了一点,以便理解。

 num_labels = 10 labels_batch = [2, 3, 5, 9] sparse_labels = tf.reshape(labels_batch, [-1, 1]) derived_size = len(labels_batch) indices = tf.reshape(tf.range(0, derived_size, 1), [-1, 1]) concated = tf.concat(1, [indices, sparse_labels]) labels = tf.sparse_to_dense(concated, [derived_size, num_labels], 1.0, 0.0) 

如上面提到的@dga, Tensorflow现在有了tf.one_hot :

 labels = tf.constant([5,3,2,4,1]) highest_label = tf.reduce_max(labels) labels_one_hot = tf.one_hot(labels, highest_label + 1) array([[ 0., 0., 0., 0., 0., 1.], [ 0., 0., 0., 1., 0., 0.], [ 0., 0., 1., 0., 0., 0.], [ 0., 0., 0., 0., 1., 0.], [ 0., 1., 0., 0., 0., 0.]], dtype=float32) 

你需要指定深度,否则你会得到一个修剪的单热张量。

如果您想手动执行此操作:

 labels = tf.constant([5,3,2,4,1]) size = tf.shape(labels)[0] highest_label = tf.reduce_max(labels) labels_t = tf.reshape(labels, [-1, 1]) indices = tf.reshape(tf.range(size), [-1, 1]) idx_with_labels = tf.concat([indices, labels_t], 1) labels_one_hot = tf.sparse_to_dense(idx_with_labels, [size, highest_label + 1], 1.0) array([[ 0., 0., 0., 0., 0., 1.], [ 0., 0., 0., 1., 0., 0.], [ 0., 0., 1., 0., 0., 0.], [ 0., 0., 0., 0., 1., 0.], [ 0., 1., 0., 0., 0., 0.]], dtype=float32) 

注意在tf.concat()中的参数顺序

 In [7]: one_hot = tf.nn.embedding_lookup(np.eye(5), [1,2]) In [8]: one_hot.eval() Out[8]: array([[ 0., 1., 0., 0., 0.], [ 0., 0., 1., 0., 0.]]) 

适用于TF版本1.3.0。 截至2017年9月。