self.biases_v4+self.weights_v5+self.biases_v5,
                                                                options = {'maxiter': 50,
                                                                          'maxfun': 50000,
                                                                          'maxcor': 50,
                                                                          'maxls': 50,
                                                                           'ftol' : 1.0 * np.finfo(float).eps})
        self.optimizer_Adam = tf.train.AdamOptimizer() 
        self.loss_v1_log = []
        self.loss_f1_log = [] 
        self.train_op_Adam_v1 = self.optimizer_Adam.minimize(self.loss1, var_list=self.weights_v1+self.biases_v1)
        self.train_op_Adam_f = self.optimizer_Adam.minimize(self.loss1 + self.lossf1, var_list=self.weights_v1+self.biases_v1+self.weights_v2+self.biases_v2+self.weights_v3+self.biases_v3+self.weights_v4+self.biases_v4+self.weights_v5+self.biases_v5)
        self.saver = tf.train.Saver()
        init = tf.global_variables_initializer()
        self.sess.run(init)
    def initialize_NN(self, layers):
        weights = []
        biases = []
        num_layers = len(layers)
        for l in range(0,num_layers-1):
            W = self.xavier_init(size=[layers[l], layers[l+1]])
            b = tf.Variable(tf.zeros([1,layers[l+1]], dtype=tf.float32), dtype=tf.float32)
            weights.append(W)
            biases.append(b) 
        return weights, biases
    def xavier_init(self, size):
        in_dim = size[0]
        out_dim = size[1]
        xavier_stddev = np.sqrt(2/(in_dim + out_dim)) 
        return tf.Variable(tf.truncated_normal([in_dim, out_dim], stddev=xavier_stddev), dtype=tf.float32)
    def neural_net(self, X, weights, biases):
        num_layers = len(weights) + 1
        X_d0 = max(self.ub[0] - self.lb[0], 1e-6)
        X_d1 = max(self.ub[1] - self.lb[1], 1e-6)
        X_d2 = max(self.ub[2] - self.lb[2], 1e-6)
        X_d = np.array([X_d0, X_d1, X_d2])
        H = 2.0*(X - self.lb)/X_d - 1.0
        for l in range(0,num_layers-2):
            W = weights[l]
            b = biases[l]
            H = tf.tanh(tf.add(tf.matmul(H, W), b))
        W = weights[-1]
        b = biases[-1]
        Y = tf.add(tf.matmul(H, W), b) 
        return Y
    def neural_net_bound(self, X, weights, biases, lower, upper):
        num_layers = len(weights) + 1
        X_d0 = max(self.ub[0] - self.lb[0], 1e-6)
        X_d1 = max(self.ub[1] - self.lb[1], 1e-6)
        X_d2 = max(self.ub[2] - self.lb[2], 1e-6)
        X_d = np.array([X_d0, X_d1, X_d2])
        H = 2.0*(X - self.lb)/X_d - 1.0
        for l in range(0,num_layers-2):
            W = weights[l]
            b = biases[l]
            H = tf.tanh(tf.add(tf.matmul(H, W), b))
        W = weights[-1]
        b = biases[-1]
        Y = tf.add(tf.matmul(H, W), b)
        scale = upper - lower
        bound_Y = scale * tf.nn.sigmoid(Y) + lower 
        return bound_Y
    def net_plasma(self, x, y, t): 
        mi_me = 3672.3036
        eta = 63.6094
        nSrcA = 20.0
        enerSrceA = 0.001
        enerSrciA = 0.001
        xSrc = -0.15
        sigSrc = 0.01
        B = (0.22+0.68)/(0.68 + 0.22 + a0*x) #check
        eps_R = 0.4889
        eps_v = 0.3496
        alpha_d = 0.0012
        tau_T = 1.0
        kappa_e = 7.6771
        kappa_i = 0.2184
        eps_G = 0.0550
        eps_Ge = 0.0005 
        v1 = self.neural_net(tf.concat([x,y,t], 1), self.weights_v1, self.biases_v1)
        v2 = self.neural_net(tf.concat([x,y,t], 1), self.weights_v2, self.biases_v2)
        v3 = self.neural_net_bound(tf.concat([x,y,t], 1), self.weights_v3, self.biases_v3, -2.0, 2.0)
        v4 = self.neural_net_bound(tf.concat([x,y,t], 1), self.weights_v4, self.biases_v4, -2.0, 2.0)
        v5 = self.neural_net_bound(tf.concat([x,y,t], 1), self.weights_v5, self.biases_v5, 0.0, 5.0)
        PINN_v2 = v2
        PINN_v3 = v3
        PINN_v4 = v4
        PINN_v5 = v5 
        v1_t = tf.gradients(v1, t)[0]
        v1_x = tf.gradients(v1, x)[0]
        v1_y = tf.gradients(v1, y)[0]
        v2_x = tf.gradients(PINN_v2, x)[0]
        v2_y = tf.gradients(PINN_v2, y)[0]
        v5_t = tf.gradients(v5, t)[0]
        v5_x = tf.gradients(v5, x)[0]
        v5_y = tf.gradients(v5, y)[0] 
        pe = v1*v5
        pe_y = tf.gradients(pe, y)[0]
        jp = v1*((tau_T**0.5)*v4 - v3) 
        lnn = tf.log(v1)
        lnn_x = tf.gradients(lnn, x)[0]
        lnn_xx = tf.gradients(lnn_x, x)[0]
        lnn_xxx = tf.gradients(lnn_xx, x)[0]
        lnn_xxxx = tf.gradients(lnn_xxx, x)[0] 
        lnn_y = tf.gradients(lnn, y)[0]
        lnn_yy = tf.gradients(lnn_y, y)[0]
        lnn_yyy = tf.gradients(lnn_yy, y)[0]
        lnn_yyyy = tf.gradients(lnn_yyy, y)[0] 
        Dx_lnn = -((50./DiffX_norm)**2.)*lnn_xxxx
        Dy_lnn = -((50./DiffY_norm)**2.)*lnn_yyyy
        D_lnn = (Dx_lnn + Dy_lnn) 
        lnTe = tf.log(v5)
        lnTe_x = tf.gradients(lnTe, x)[0]
        lnTe_xx = tf.gradients(lnTe_x, x