Python 3.6上的TensorFlow-如何避免会话创建开销

时间:2018-08-08 09:12:32

标签: python tensorflow python-3.6

我在TF上运行了一个简单的斩首DCNN(Incepton-V3 w ImageNet权重),并且从TF 1.0.1 / PY 35迁移到TF 1.9 / PY 36(都在Windows7上使用了Anaconda),我的运行时间增加了近2倍(使用几乎相同的代码)。

更多细节-

在较旧的环境(Py3.5 TF1.0.1)中,我在开放式会话中使用过,例如:

def image_extract_features(sess, allTensors, imgfilename):
    imgdata = read_file(imgfilename)
    imgResized = sess.run(readTensor, {dataTensor: imgdata})
    imgEmbed = sess.run(bottlenecktensor, {resizedTensor: imgResized})
    return imgEmbed

sess, graph, allTensors, modelInfo = initiate_graph(modelDir)
for _ in range(100):
    imgfilename = browseFileName()
    if not imgfilename:
        break
    feats = image_extract_features(sess, allTensors, imgfilename)

当我在新环境(Py3.6 / TF)上运行它时,出现错误:

RuntimeError: Attempted to use a closed Session.

所以我尝试了

def image_extract_features(graph, allTensors, imgfilename):
    ...
    with tf.Session(graph=graph) as sess:
        imgResized = sess.run(readTensor, {dataTensor: imgdata})
        imgEmbed = sess.run(bottlenecktensor, {resizedTensor: imgResized})
    return imgEmbed

这是我每个图像的运行时间增加约2倍的地方(从〜0.5到〜1秒)。 此外,使用Keras(显而易见的方式)运行相同图像,每张图像的时间约为0.9秒。

目标-在我的计算机上,每张图片恢复到约0.5秒。

为了巩固我对会话创建的怀疑,并且知道图像解码和调整大小相对较快,我编写了以下循环:

from time import time as now
with tf.Session(graph=graph) as sess:
    t = [now()]
    for imgfile in imgfiles:
        imgResized = sess.run(readTensor, {dataTensor: open(imgfile, 'rb').read()})
        t.append( now() )
    (np.diff(t)*1000).astype(int).tolist()

在3个文件的列表中,给出了以下结果:

[378,   4,  19] # Runtime per file [ms]

随机播放并重新运行。得到了:

[371,  10,   5] # Runtime per file [ms]

因此,我们看到创建会话之后的第一项要慢得多。

我的最后一个问题是:鉴于我的申请是

  • 获取图像文件
  • 斩首DCNN
  • 利用所产生的功能做些事情

并且我无法打开会话,该如何避免这种新的会话开销?

谢谢

1 个答案:

答案 0 :(得分:0)

似乎有些更改导致<script language="javascript" type="text/javascript"> function GetGroup(_serviceId) { $.ajax({ url: '@Url.Action("GetGroupByService", "Components")', data: { serviceId: _serviceId }, cache: false, type: "POST", success: function (data) { var markup = ""; for (var x = 0; x < data.length; x++) { if (data[x].serviceId == _serviceId) { markup += "<option value=" + data[x].groupId + ">" + data[x].groupName + "</option>"; } } $("#GroupId").html(markup).show(); }, error: function (reponse) { alert("error : " + reponse); } }); } </script> 由于某种原因返回了无效的会话。如果您不想或者无法调查或解决该问题,则可以忽略它并进行自己的会话,并保持相同的原始代码结构。

<label asp-for="ServiceId" class="control-label">Service Name</label>
<select asp-for="ServiceId" class="form-control" asp-items="ViewBag.ServiceName" onchange="javascript:GetGroup(this.value);">

<label asp-for="GroupId" class="control-label">Group Name</label>
<select asp-for="GroupId" name="GroupId" class="form-control"></select>

此外,您始终可以创建会话并将其存储在变量中(例如initiate_graph,而不是在def image_extract_features(sess, allTensors, imgfilename): imgdata = read_file(imgfilename) imgResized = sess.run(readTensor, {dataTensor: imgdata}) imgEmbed = sess.run(bottlenecktensor, {resizedTensor: imgResized}) return imgEmbed _, graph, allTensors, modelInfo = initiate_graph(modelDir) with tf.Session(graph=graph) as sess: for _ in range(100): imgfilename = browseFileName() if not imgfilename: break feats = image_extract_features(sess, allTensors, imgfilename) 块中使用它),然后根据需要多次使用。您只需要确保在不再需要它时就将其关闭(例如,使用sess = tf.Session() / with块)。