1. 程式人生 > >TensorFlow程式設計入門(一)

TensorFlow程式設計入門(一)

寫在最前

深度學習辣麼火,感覺應該學習學習以免以後人家講座什麼的聽不懂。因此想要從應用層面出發,學習學習,那就看看怎麼用tensorflow(以下簡稱tf)做神經網路吧。這裡看的是莫煩大大的視訊,真心強烈安利:視訊地址

Tensorflow 基礎構架

本章主要講解tensorflow主要的元素,其中包括會話session,變數variable,傳入值placeholder,激勵函式Activation Function。下面的程式碼是一個簡單的tf程式的例項:

# coding:utf-8
import tensorflow as tf
import numpy as np

x_data = np.random.rand(100
).astype(np.float32) # 生成100個隨機數,型別是float32 y_data = x_data*0.1+0.3 Weights = tf.Variable(tf.random_uniform([1],-1.0,1.0)) # tf.Variable是用來生成tf變數,這裡就是生成一個[-1,1]數 biases = tf.Variable(tf.zeros([1])) # zeros可以生成一個0 y = Weights*x_data+biases # 針對每個x算出y值 loss = tf.reduce_mean(tf.square(y-y_data)) # 計算loss 平方求平均
optimizer = tf.train.GradientDescentOptimizer(0.5) # 找個訓練方法就是什麼梯度下降之類的 train = optimizer.minimize(loss) # 訓練,讓loss最小 init = tf.initialize_all_variables() # 初始化所有的變數 sess = tf.Session() # 會話,賊重要 sess.run(init) # 啥也得run才可以 print sess.run(Weights) for step in range(201): sess.run(train) if step % 20
== 0: print step,sess.run(Weights),sess.run(biases)

會話Session

session是個執行命令的東西,用來執行tf圖上的某個小的功能。就是啥也要用sess.run一下啦。這裡演示一個簡單的矩陣乘法:

# coding:utf-8
import tensorflow as tf

matrix1 = tf.constant([[3,3]])
matrix2 = tf.constant([[2],
                       [2]])
product = tf.matmul(matrix1,matrix2)  # matrix multiply np.dot(m1,m2)

這裡定義了兩個矩陣,而product是兩個矩陣相乘的結果。但是,只是這樣是無法得到結果的。因此需要session來執行,有兩種方法:
方法一:

sess = tf.Session()
result = sess.run(product)
print result
sess.close()

方法二:

with tf.Session() as sess: # 自動關
    result2 = sess.run(product)
    print result2

變數Variable

下面有個例子能直觀表現sess.run和變數的作用。

state = tf.Variable(0,name='counter')
one = tf.constant(1)
new_value = tf.add(state,one) # state+1的值賦給new_value
update = tf.assign(state,new_value) # 更新state的值

init = tf.initialize_all_variables() # 必須初始化

with tf.Session() as sess:
    sess.run(init)
    for _ in range(3): # 更新3次
        sess.run(update)
        print sess.run(state)

 這個方法輸出1,2,3三個數。這可以看出,sess.run就是運行了一下update獲得這個值。

placeholder

 placeholder的作用就是先給資料佔個位置,在需要的時候再傳入。

# coding:utf8
import tensorflow as tf
import numpy as np

input1 = tf.placeholder(tf.float32)
input2 = tf.placeholder(tf.float32)

output = tf.mul(input1,input2)

with tf.Session() as sess:
    print (sess.run(output,feed_dict={input1:[7.],input2:[2.]})) # placeholder和feed_dict是繫結的

顯而易見,最後輸出的值是14.

激勵函式

 這個激勵函式通常是sigmoid函式,當然還有很多,自己google吧~

建造神經網路

 最主要的函式就是add_layer()了,然後所有東西都在註釋裡了:

# coding:utf8
import tensorflow as tf
import numpy as np
import matplotlib.pyplot as plt

def add_layer(inputs,in_size,out_size,n_layer,activation_function=None):
    layer_name = 'layer%s'% n_layer
    with tf.name_scope(layer_name): # 意思是這個with裡的元素被包括在scope裡
        with tf.name_scope('weights'):
            Weights = tf.Variable(tf.random_normal([in_size,out_size]),name='W') # 就是建造一個數組,[行,列]
            tf.histogram_summary(layer_name+'/weights',Weights) # 讓weights
        with tf.name_scope('biases'):
            biases = tf.Variable(tf.zeros([1,out_size]) + 0.1,name='b')
            tf.histogram_summary(layer_name+'/biases',biases)
        with tf.name_scope('Wx'):
            Wx_plus_b=tf.matmul(inputs,Weights) + biases # 計算一波
        if activation_function is None: # 如果不指定激勵函式
            outputs = Wx_plus_b
        else:
            outputs = activation_function(Wx_plus_b) # 如果指定了激勵函式
        tf.histogram_summary(layer_name+'/outputs',outputs)
        return outputs

x_data = np.linspace(-1,1,300)[:,np.newaxis] # 這個能生成300個數,後面中括號可以讓它變成豎著的
noise = np.random.normal(0,0.05,x_data.shape) # 生成噪聲點,這裡是個正太分佈,均值是0方差是0.05,和x_data一樣的格式
y_data = np.square(x_data)-0.5+noise # 計算y

with tf.name_scope('inputs'):
    xs = tf.placeholder(tf.float32,[None,1],name='x_input')
    ys = tf.placeholder(tf.float32,[None,1],name='y_input')


l1 = add_layer(xs,1,10,n_layer=1,activation_function=tf.nn.relu) # 輸入資料是xs,1個輸入,10個輸出,名字是1,激勵函式是relu
predition = add_layer(l1,10,1,n_layer=2,activation_function=None) # 輸入資料是l1的輸出,10個輸入,1個輸出,名字是2,沒激勵函式
with tf.name_scope('loss'):
    loss = tf.reduce_mean(tf.reduce_sum(tf.square(ys-predition),reduction_indices=[1]))
    tf.scalar_summary('loss',loss)
with tf.name_scope('train'):
    train_step = tf.train.GradientDescentOptimizer(0.1).minimize(loss)

init = tf.initialize_all_variables()
sess = tf.Session()
merged = tf.merge_all_summaries()
writer = tf.train.SummaryWriter("logs/",sess.graph) # 將所有的圖畫到log裡
sess.run(init)

fig = plt.figure() # 用這個畫圖
ax = fig.add_subplot(1,1,1) # 圖片編號
ax.scatter(x_data,y_data) # 點的編號
plt.ion() # 不用停頓
plt.show() # 輸出圖片


for i in range(1000):
    sess.run(train_step,feed_dict={xs:x_data,ys:y_data})
    if i%50 == 0:
        result = sess.run(merged,feed_dict={xs:x_data,ys:y_data})
        writer.add_summary(result,i) # 每i步輸出一個結果
        try:
            ax.lines.remove(lines[0]) # 去除上次的線
        except Exception:
            pass
        #print sess.run(loss,feed_dict={xs:x_data,ys:y_data})
        predition_value = sess.run(predition,feed_dict={xs:x_data}) # 預測值
        lines = ax.plot(x_data,predition_value,'r-',lw=5) # 用紅色,寬度為5的曲線的形式畫出來預測曲線
        plt.pause(0.1)