zoukankan      html  css  js  c++  java
  • 用python面向对象的方法实现欧拉算法和龙格库塔算法

     1 #!/bin/python3
     2 # -*-coding:utf-8 -*-
     3 import math
     4 import numpy as np
     5 
     6 #定义一个欧拉算法的类,从而实现不同步长的引用
     7 class Euler:
     8     y_list=[]                #定义一个空列表来实现y值的存储
     9     def __init__(self, h=0.1, y0=1,):        #初始化Euler类的方法
    10         self.h = h
    11         self.y0 = y0
    12         self.y = y0
    13         self.n = 1/h
    14         self.y_list = Euler.y_list
    15 
    16     def euler(self, y0, h,):       #定义Euler算法的过程
    17         x = 0
    18         y = y0
    19         n = 1/h
    20         for i in range(int(self.n+1)):
    21             y_dere = 1 + math.log(x + 1)
    22             y += self.h * y_dere
    23             self.y_list = Euler.y_list.append("%.10f" % y)
    24 
    25 #  print("%.3f" % x, "%.10f" % y)
    26             x += self.h
    27 # print(Euler.y_list,)
    28         return np.linspace(0, 1, n+1,dtype=float), Euler.y_list   #为了引用结果列表,从而返回两个列表
    29 
    30 
    31 #定义一个实现龙格库塔方法
    32 class RungeKutta:
    33     y_list = []           #同理,设置一个空列表来储存y值
    34     def __init__(self, h=0.1, y0=1,):
    35         self.h = h
    36         self.y0 = y0
    37 
    38     def make_ks(self, x_k,y_k):
    39 
    40         def y_ders(x_k):
    41             y_der = 1 + math.log(x_k + 1)
    42             return y_der
    43 #计算K1,K2,K3,K4
    44         k1 = y_ders(x_k)
    45         k2 = y_ders(x_k + self.h/2)
    46         k3 = y_ders(x_k + (self.h/2))
    47         k4 = y_ders(x_k + self.h)
    48         y_k = y_k+self.h/6*(k1+(2-math.sqrt(2))*k2 + (2 + math.sqrt(2))*k3 + k4)
    49         return x_k, y_k
    50 
    51     def make(self, h, y0):
    52         n = int(1/self.h)
    53         y_k = y0
    54         x_k = 0
    55         for i in range(n):          #用循环遍历来实现y值的计算
    56             x_k, y_k = self.make_ks(x_k,y_k)
    57             x_k += h
    58 # print("%.3f" % x_k, "%.10f" % y_k)
    59             RungeKutta.y_list.append("%.10f" % y_k)
    60 
    61         return np.linspace(0, 1, 1/h+1, dtype=float), RungeKutta.y_list
    62 
    63 
    64 #下面将收集计算的值,首先输出Euler法,再输出rungkutta,x,y数据的顺序是:x,y
    65 print("Euler", "h=0.1")
    66 a1 = Euler()
    67 ax1, ay1 = a1.euler(h=0.1, y0=1)
    68 print(ax1, "
    ", ay1)
    69 print("----------------------------------------------------------------------------")
    70 print("Euler", "h=0.1")
    71 print("h=0.01")
    72 a2 = Euler()
    73 ax2, ay2 = a2.euler(h=0.01, y0=1)
    74 print(ax2, "
    ", ay2)
    75 print("----------------------------------------------------------------------------")
    76 print("Euler", "h=0.1")
    77 print("h=0.2")
    78 a3 = Euler()
    79 ax3, ay3 = a3.euler(h=0.2, y0=1)
    80 print(ax3, "
    ", ay3)
    81 print("----------------------------------------------------------------------------")
    82 
    83 print("Rungkutta", "h=0.2")
    84 c1 = RungeKutta(h=0.2, y0=1)
    85 cx1, cy1 = c1.make(h=0.2, y0=1)
    86 print(cx1, "
    ", cy1)
    87 print("-----------------------------------------------------------------------------")
    88 
    89 print("Rungkutta", "h=0.1")
    90 c2 = RungeKutta(h=0.1, y0=1)
    91 cx2, cy2 = c2.make(h=0.1, y0=1)
    92 print(cx2, "
    ", cy2)
    93 print("-----------------------------------------------------------------------------")
    94 
    95 print("Rungkutta", "h=0.01")
    96 c3 = RungeKutta(h=0.01, y0=1)
    97 cx3, cy3 = c3.make(h=0.01, y0=1)
    98 print(cx3, "
    ", cy3)
    99 print("-----------------------------------------------------------------------------")

    以上的代码是实现算法的过程,以及输出的部分,还可以加入自定义的文件读取的办法,以及其他存储方式保存数据结果。

    》》》》》》》》》》》》》》》》》》》》》》

    程序2.0版本:

    》》》》》》》》》》》》》》》》》》》》》》

    # -*-coding:utf-8 -*-
    import math
    import numpy as np
    import matplotlib.pyplot as plt
    
    
    # 定义一个欧拉算法的类,从而实现不同步长的引用
    
    
    class Euler:
        # y_list = []  # 定义一个空列表来实现y值的存储
    
        def __init__(self, h,  y0):  # 初始化Euler类的方法
            self.h = h
            self.y0 = y0
            self.y = y0
            self.n = 1 / self.h
            self.x = 0
    
        def euler(self):  # 定义Euler算法的过程
            # x = 0
            #  y = self.y0
            # n = 1 / self.h
            for i in range(int(self.n + 1)):
                y_dere = 1 + math.log(self.x + 1)
                self.y += self.h * y_dere
                self.y_list = Euler_y_list.append("%.10f" % self.y)
                self.x += self.h
            # print(Euler.y_list,)
            return np.linspace(0, 1, self.n + 1, dtype=float), Euler_y_list  # 为了引用结果列表,从而返回两个列表
    
    
    # 定义一个实现龙格库塔方法
    class RungeKutta:
    
        def __init__(self, h, y0=1):
            self.h = h
            self.y0 = y0
    
        def make_ks(self, x_k, y_k):
            def y_ders(x_k):
                y_der = 1 + math.log(x_k + 1)
                return y_der
    
            # 计算K1,K2,K3,K4
            k1 = y_ders(x_k)
            k2 = y_ders(x_k + self.h / 2)
            k3 = y_ders(x_k + (self.h / 2))
            k4 = y_ders(x_k + self.h)
            y_k = y_k + self.h / 6 * (k1 + (2 - math.sqrt(2)) * k2 + (2 + math.sqrt(2)) * k3 + k4)
            return x_k, y_k
    
        def make(self):
            n = int(1 / self.h)
            y_k = self.y0
            x_k = 0
            for i in range(n):  # 用循环遍历来实现y值的计算
                x_k, y_k = self.make_ks(x_k, y_k)
                x_k += self.h
                RungeKutta_y_list.append(y_k)
    
            return np.linspace(0, 1, n+1, endpoint=True,dtype=float), RungeKutta_y_list
    
    
    class Plots:
        def __init__(self, x, y, title):
            self.x = list(x)
            self.y = list(y)
            self.title = title
    
        def plots(self):
            plt.figure(figsize=(8, 4))
            plt.scatter(self.x, self.y, label="y'=1+ln(x+1),
    y0=1
    (0<x<=1) ", color="red", linewidth=2)
            plt.xlabel("x")
            plt.ylabel("y")
            plt.title(self.title)
          #  plt.ylim(min(self.y), max(self.y))
            plt.ylim()
            plt.legend()
            plt.show()
    
    
    if __name__ == "__main__":
         while True:
            name = input("本程序提供Euler算法和Rungekutta算法
    选择算法时输入exit退出
    请输入需要的算法名:")
            try:
                 a = float(input("请输入所需要的h值:"))
                 if  a =="exit" or a=="Exit":
                     break
            except ValueError as ve:
                print(ve)
            if name == "Euler":
                Euler_y_list =[]
                l1 = Euler(h=a, y0=1)
                l1x, l1y = l1.euler()
                with open("Euler.txt","a+") as f:
                    f.write("h=%s
    " % l1.h)
                    f.write("x值--------------y值
    ")
                    for i in range(len(l1x)):
                         print("x是:%.5f  y是:%.10f" % (float(l1x[i]),float(l1y[i])))
                         a,b = str(l1x[i]),str(l1y[i])
                         f.write(a+" "*6+b+"
    ")
                l1p = Plots(l1x, l1y, name)
                l1p.plots()
                print("请储存好你的x值,和y值")
                del l1, l1p, l1x, l1y
                Euler.y_list = []
            elif name == "Rungekutta":
                RungeKutta_y_list = [0]
                l2 = RungeKutta(h=a)
                l2x, l2y = l2.make()
                with open("Rungekutta.txt", "a+") as f:
                    f.write("h=%s
    " % l2.h)
                    f.write("x值--------------y值
    ")
                    for i in range(len(l2x)):
                         print("x是:%.5f  y是:%.10f" % (l2x[i], l2y[i]))
                         a, b = str(l2x[i]), str(l2y[i])
                         f.write(a + " " * 6 + b + "
    ")
                l2p = Plots(l2x, l2y, name)
                l2p.plots()
                print("请储存好你的x值,和y值")
                del l2, l2p
            elif name =="exit":
                break
            else:
                print("请输入正确的算法名!!!!")

    加入了退出和写入到文件的功能

  • 相关阅读:
    SVM
    决策树
    神经网络
    机器学习之降维方法
    机器学习之特征选择
    浏览器状态码大全
    哈希表
    社区发现算法总结(二)
    社区发现算法总结(一)
    聚类篇-------度量
  • 原文地址:https://www.cnblogs.com/BlogOfMr-Leo/p/8537097.html
Copyright © 2011-2022 走看看