如何从Tensorflow上的Softmax图层中提取预测

时间:2018-05-25 22:54:54

标签: python tensorflow prediction softmax categorization

我试图提取预测,在计算准确度/精确度/召回率/ F1和预测概率时使用预测。我知道我有10个输出类,因此我不能计算每次看到的精度,但我将在其他模型中完成所有这些,而且我希望能够提取预测概率。我的模型如下。我已经检查过GitHub和StackOverflow但是我还没有找到提取这些属性的方法。大多数答案都很接近,但从来没有回答我的需要。我在那里使用了一些低纪元数字,以便快速检查模型并保持输出屏幕不那么拥挤。

import tensorflow as tf
from tensorflow.contrib.layers import fully_connected

from sklearn.datasets import fetch_mldata
from sklearn.preprocessing import LabelBinarizer
from sklearn.model_selection import train_test_split

mnist = fetch_mldata('MNIST original', data_home="data/mnist/")
lb = LabelBinarizer().fit(mnist.target)
X_train, X_test, y_train, y_test = train_test_split(mnist.data, lb.transform(mnist.target), train_size=0.9, test_size=0.1)

X = tf.placeholder(tf.float32, shape=(None, 784))
y = tf.placeholder(tf.int64, shape=(None, 10))

lOne = fully_connected(inputs=X, num_outputs=100, activation_fn=tf.nn.elu)
logits = fully_connected(inputs=lOne, num_outputs=10, activation_fn=tf.nn.softmax)

pred = logits
acc = tf.metrics.accuracy(labels=y, predictions=pred)

loss = tf.losses.softmax_cross_entropy(logits=logits, onehot_labels=y)
trainOP = tf.train.AdamOptimizer(0.001).minimize(loss)

import numpy as np
bSize = 100
batches = int(np.floor(X_train.shape[0]/bSize)+1)
def batcher(dSet, bNum):
    return(dSet[bSize*(bNum-1):bSize*(bNum)])

epochs = 2
init = tf.global_variables_initializer()
with tf.Session() as sess:
    sess.run(init)
    for epoch in range(0, epochs):
        for batch in range(1, batches):
            X_batch = batcher(X_train, batch)
            y_batch = batcher(y_train, batch)
            sess.run(trainOP, feed_dict={X: X_batch, y: y_batch})
        lossVal = sess.run([loss], feed_dict={X: X_test, y: y_test})
        print(lossVal)


    sess.close()

2 个答案:

答案 0 :(得分:1)

问题中分享的代码涵盖了培训,但没有"使用" (推断)与结果模型。

两个问题:

  • 经过训练的模型未被序列化,因此将来的运行将在未经训练的模型上运行,并预测其初始化告诉他们的任何内容。因此question comment建议保存训练的模型,并在预测时恢复它。
  • logits是SoftMax函数的输出。从logits中获取类的一种常用方法是选择张量中的最高值(此处为向量)。

使用TensorFlow,最后一点可以使用tf.argmax完成("返回张量轴上具有最大值的索引。"):

tf.argmax(input=logits, axis=1)

总而言之,问题的代码仅部分涵盖了TensorFlow团队的MNIST tutorial。如果你遇到这个代码,可能会有更多的指示。

答案 1 :(得分:0)

我写的是以防任何人可能偶然发现这个特例。我已经按照基本的MNIST示例构建了一个网络,我在最后一层使用了tf.nn.softmax,并期望从所述层获得结果。看起来我需要再次使用softmax函数来获取yPred = tf.nn.softmax(logits)等层的结果,其中logits是输出层的名称。我在下面添加了固定代码。

我可以添加一行来保存模型,稍后加载它并对保存的模型进行预测。由于这只是我构建模型的一个例子,我省略了保存部分。

import tensorflow as tf
from tensorflow.contrib.layers import fully_connected

from sklearn.datasets import fetch_mldata
from sklearn.preprocessing import LabelBinarizer
from sklearn.model_selection import train_test_split

mnist = fetch_mldata('MNIST original', data_home="data/mnist/")
lb = LabelBinarizer().fit(mnist.target)
X_train, X_test, y_train, y_test = train_test_split(mnist.data, lb.transform(mnist.target), train_size=0.9, test_size=0.1, stratify = mnist.target, random_state=42)

X = tf.placeholder(tf.float32, shape=(None, 784))
y = tf.placeholder(tf.int64, shape=(None, 10))


lOne = fully_connected(inputs=X, num_outputs=100, activation_fn=tf.nn.elu)
lTwo = fully_connected(inputs=lOne, num_outputs=100, activation_fn=tf.nn.elu)
logits = fully_connected(inputs=lTwo, num_outputs=10, activation_fn=tf.nn.softmax)

pred = tf.nn.softmax(logits)
acc_bool = tf.equal(tf.argmax(logits, 1), tf.argmax(y, 1))
acc_Num = tf.cast(acc_bool, tf.float32)
acc_Mean = tf.reduce_mean(acc_Num)

loss = tf.losses.softmax_cross_entropy(logits=logits, onehot_labels=y)
trainOP = tf.train.AdamOptimizer(0.001).minimize(loss)


import numpy as np
bSize = 1024
batches = int(np.floor(X_train.shape[0]/bSize)+1)
def batcher(dSet, bNum):
    return(dSet[bSize*(bNum-1):bSize*(bNum)])



epochs = 250
init = tf.global_variables_initializer()
trainA = []
testA = []

with tf.Session() as sess:
sess.run(init)
for epoch in range(0, epochs):
    for batch in range(1, batches):
        X_batch = batcher(X_train, batch)
        y_batch = batcher(y_train, batch)
        sess.run(trainOP, feed_dict={X: X_batch, y: y_batch})
    if epoch % 25 == 1:
        trainLoss, trainAcc = sess.run([loss, acc_Mean], feed_dict={X: X_train, y: y_train})
        testLoss, testAcc = sess.run([loss, acc_Mean], feed_dict={X: X_test, y: y_test})
        yPred = sess.run(pred, feed_dict={X: X_test[0].reshape(1,-1), y: y_test[0].reshape(1,-1)})
        print(yPred)

sess.close()