tensorflow运行模式

一个c++或者java,python程序员,一开始接触到tensorflow,必然会被其运行方式所迷惑。 因为tensorflow是先构图,再执行。c=tf.add(a,b),在执行这行代码时,只是在构图,并没有进行计算。所以进行print(c)时,只是打出来了未计算的结点引用。

然而,tensorflow这种先构图再计算的方式,并不是首创。像spark, flink这两个计算引擎也是先构图再执行。因此构图也是一种解决问题的模式。 而且还能进行图优化,非常适合分布式计算任务。在游戏引擎中大名鼎鼎的UE4引擎,支持蓝图式编程。可以看作是手动构图。非常适合非程序员职业的人构建程序。而tensorflow是用python去构图,还是有一定的门槛。

从tensorflow2.0开始默认会启动Eager, 这种eager模式下,所有计算会立即执行,非常方便调试。

下面以一个计算1+2+3+...+100的例子来演示它们的区别。

普通python计算

sum = 0 #变量sum用于累计
for i in range(1, 101): #1到100
    sum += i
print(sum) #输出

5050

ue5蓝图

蓝图是手动构建图。不用编程。

tensorflow

while_loop的核心要求,conditiion, loop_body的输入参数就是loop_vars

loop_body返回值也必须是loop_vars, 参数数量必须一样

condition的返回值是bool类型的tensor

while_loop返回的也是loop_body最后返回的

import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()
tf.disable_eager_execution ()


def condition(i, v): #循环结束条件
    return i <= 100

def loop_body(i, v):
    return i + 1, v + i #输入i,v,返回必须也是两个形状类型相同的tensor,会再次输入

i, v = 1, 0 #初始循环变量值
ii, vv = tf.while_loop(condition, loop_body, loop_vars=[i, v]) #这里相当于ue5中蓝图里的for_loop结点

#以上是构图,下面执行图得到结果
with tf.Session() as sess:
    print(sess.run([ii, vv]))

#最后输出:[101, 5050]
import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()
tf.disable_eager_execution ()

i = tf.Variable(1)
v = tf.Variable(0)

def condition(i, v):
    return i <= 100

def loop_body(i, v):
    i += 1
    v += i
    return i, v

ii, vv = tf.while_loop(condition, loop_body, loop_vars=[i, v])

init_op = tf.global_variables_initializer()
#导出图
summary_writer = tf.summary.FileWriter('tb_log/',  flush_secs=1)
with tf.Session() as sess:
    sess.run([init_op])
    print(sess.run([ii, vv]))
    summary_writer.add_graph(sess.graph)#添加graph图
summary_writer.close()

#运行tensorboard
#tensorboard --logdir tb_log
#然后打开浏览器就能查看:http://localhost:6006/#graphs&run=.

从图中可以看出,两个变量分别是i,v。while中的两个add和一个less_equal对就了loop_body,和condition 

加上变量名再展示会更好:

import tensorflow.compat.v1 as tf
tf.disable_v2_behavior()
tf.disable_eager_execution ()

i = tf.Variable(1, name="i")
v = tf.Variable(0, name="v")

def condition(i, v):
    return tf.less_equal(i, 100, name="ile100")

def loop_body(i, v):
    i = tf.add(i, 1, name="addi")
    v = tf.add(i, v, name="addiv")
    return i, v

ii, vv = tf.while_loop(condition, loop_body, loop_vars=[i, v])

init_op = tf.global_variables_initializer()
summary_writer = tf.summary.FileWriter('tb_log/',  flush_secs=1)
with tf.Session() as sess:
    sess.run([init_op])
    print(sess.run([ii, vv]))
    summary_writer.add_graph(sess.graph)#添加graph图
summary_writer.close()

Spark DAG

如下代码,只有在执行collect时才真正开始提交运行图。而上边的代码都是在构图,实际并未运行

Flink DAG

Flink 原理与实现:架构和拓扑概览

flink中级篇-DAG图的剖析_kangzai98的博客-CSDN博客_dag图解析

C++也能构图后延时计算:boost phoniex

看到下图中的for_,是延时执行的。采用lambda延时计算技术,可以达到类似构图再计算的效果。

for_ Statement - 1.64.0

#include <boost/phoenix/statement/for.hpp>
int iii;
std::for_each(c.begin(), c.end(),
    (
        for_(ref(iii) = 0, ref(iii) < arg1, ++ref(iii))
        [
            cout << arg1 << ", "
        ],
        cout << val("\n")
    )
);

使用计算图的优势

1. 图是抽象的,与实现无关:比如tf.add这么一个OP, 也就是图中的一个结点.只是定义了一个加法和其输入输出参数,多个结点连接形成的计算图也是抽象的描述了整个计算程序。可看做是声明式编程的一种方式。

2. 不同平台不同实现:图构建好后,可以直接跨平台运行。不同平台只要实现自己的add kernel即可。特别的,比如GPU与CPU的实现可能不同。ARM和x86实现不同。服务器与Android客户端可以实现不同。

3. 优化与剪枝:可以对图进行各种优化,提高性能

4. 分布式并行计算:分析图可以得到哪些计算可以并行,就可以调度到不同机器上并行计算机。同样图可以分块拆解,并放到不同机器上执行。

   例如PS-Worker架构,就是把图中的variable等存储结点拆解到PS上。而计算结点拆解到Worker上,并在中间插入通信代码。可见计算图做这种事十分方便。相反,如果是一段C++或者python代码,想这么做就很困难。

可以计算图是受限制的代码。每个结点看做一个抽象的函数。在计算图中没有面向对象编程,也无法搞复杂设计模式。其简单性能,边界性虽然给实现功能带来了困难,但是,给分布式执行,自动优化等提供了方便。

  • 2
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: 要在TensorFlow 2.中运行1.代码,您需要使用TensorFlow 1.x兼容性模块。这个模块可以让您在TensorFlow 2.中使用1.代码,但是您需要注意一些细节,例如变量初始化和会话管理。您可以使用以下代码导入兼容性模块: ``` import tensorflow.compat.v1 as tf tf.disable_v2_behavior() ``` 然后,您可以使用1.代码,例如: ``` x = tf.placeholder(tf.float32, shape=[None, 784]) W = tf.Variable(tf.zeros([784, 10])) b = tf.Variable(tf.zeros([10])) y = tf.nn.softmax(tf.matmul(x, W) + b) ``` 请注意,您需要使用`tf.Session()`来运行计算图: ``` with tf.Session() as sess: sess.run(tf.global_variables_initializer()) result = sess.run(y, feed_dict={x: input_data}) ``` 希望这可以帮助您在TensorFlow 2.中运行1.代码。 ### 回答2: 在TensorFlow 2.0中运行1.0版本的代码有一些注意事项。由于TensorFlow 2.0是向后兼容的,可以运行1.0版本的代码,但需要进行一些修改。TensorFlow 2.0默认使用了eager execution(即即时执行)模式,而1.0版本默认使用了静态图模式。以下是几个需要注意的地方: 1. 导入库:在TensorFlow 2.0中,需要使用`import tensorflow.compat.v1 as tf`来导入1.0版本的tensorflow库。这样可以确保使用1.0版本的API和函数。 2. 静态图模式TensorFlow 2.0的默认模式是即时执行模式(eager execution),如果想要使用1.0版本的静态图模式,需要使用`tf.compat.v1.disable_eager_execution()`来禁用即时执行。 3. placeholder:在TensorFlow 2.0中,`tf.placeholder`已经被移除了。可以使用`tf.compat.v1.placeholder`来代替。 4. Session:在TensorFlow 2.0中,可以直接运行张量,不再需要Session。如果代码中有`Session`相关的操作,需要将其修改为直接执行相应的操作。 5. 变量声明:在TensorFlow 2.0中,`tf.Variable`的默认行为有一些变化。如果想要使用1.0版本的变量声明行为,可以使用`tf.compat.v1.Variable`来代替。 需要注意的是,并非所有1.0版本的代码都可以无修改地在2.0版本上运行,特别是那些使用了一些被废弃的API和函数的代码。因此,在运行1.0版本的代码时,需要根据代码的具体情况进行相应的修改和调整,以确保代码在TensorFlow 2.0上能够正常运行。 ### 回答3: TensorFlow 2.0是相对于早期版本的重大升级,其中包含了许多新特性和改进。因此,如果要在TensorFlow 2.0中运行1.0的代码,可能会遇到一些兼容性问题。以下是一些可能需要处理的问题: 1. 语法差异:TensorFlow 2.0对许多API进行了重大的修改和重命名。因此,1.0版本的代码可能包含已被弃用或删除的函数和参数。需要修改代码以适应新的API。 2. Eager Execution:TensorFlow 2.0默认启用了Eager Execution,这是一个即时执行模式。而1.0版本默认使用的是图计算模式。因此,在运行1.0代码时,可能需要禁用Eager Execution或者修改代码以适应新的执行模式。 3. Keras集成:TensorFlow 2.0将Keras作为其主要的高级API。因此,如果1.0代码使用了其他的高级API,可能需要将其转换为Keras的形式,并使用新的Keras API进行模型构建和训练。 4. 数据集处理:TensorFlow 2.0引入了tf.data API,用于高效处理和预处理数据集。1.0版本中的代码可能使用了不同的数据处理方式,需要修改以适应新的API。 总之,将1.0代码迁移到TensorFlow 2.0需要根据具体的代码进行相应的调整和修改,以适应新版本的语法和功能。但是,由于TensorFlow团队一直致力于保持向后兼容性,因此许多代码可以在2.0版本中无修改地继续运行

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值