From fbcafa4686742ddd8f17345451add1406c1b42e6 Mon Sep 17 00:00:00 2001 From: andrei Date: Fri, 1 Nov 2024 11:23:12 +0300 Subject: [PATCH] =?UTF-8?q?chore:=20=D1=83=D0=B1=D1=80=D0=B0=D0=BB=20?= =?UTF-8?q?=D0=BD=D0=B5=D0=B8=D1=81=D0=BF=D0=BE=D0=BB=D1=8C=D0=B7=D1=83?= =?UTF-8?q?=D0=B5=D0=BC=D1=8B=D0=B5=20=D1=84=D0=B0=D0=B9=D0=BB=D1=8B?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- OptAlgorithm.py | 223 ------------------------------------------- OptTimeCalculator.py | 148 ---------------------------- params.json | 19 ---- 3 files changed, 390 deletions(-) delete mode 100644 OptAlgorithm.py delete mode 100644 OptTimeCalculator.py delete mode 100644 params.json diff --git a/OptAlgorithm.py b/OptAlgorithm.py deleted file mode 100644 index d3fdc1c..0000000 --- a/OptAlgorithm.py +++ /dev/null @@ -1,223 +0,0 @@ -from OptTimeCalculator import OptTimeCalculator -from Params import Params -from numpy import cos, sin, sqrt, cbrt, arcsin, linspace - -class OptAlgorithm(): - - paramsPath = "." - paramsFile = "params.json" - def __init__(self, useMins = True, s1 = 0, s2 = 0): - self.p = Params(OptAlgorithm.paramsPath, OptAlgorithm.paramsFile) - calc = OptTimeCalculator(self.p) - if useMins: - s1 = self.p.smin1t - s2 = self.p.smin2t - calc.T(s = s1, s2 = s2) - self.Ts = calc.Ts - self.TStartOpen = sqrt(self.p.flon / self.p.k * 2 / self.p.a) - self.T2 = calc.calcSecond(Tstart = self.TStartOpen, s2 = s2) - - self.x1Contact = s1 + self.p.x10 - self.x2Contact = s2 + self.p.x20 - - def V1Close(self, t: float): - if t < self.Ts["t1"]: - return self.p.a * t - else: - return self.p.a * self.Ts["t1"] - - def X1Close(self, t: float): - t1 = min(t, self.Ts["t1"]) - x0 = self.p.a * t1 * t1 / 2 - - t2 = max(t - self.Ts["t1"], 0) - x1 = self.p.a * self.Ts["t1"] * t2 - - return x0 + x1 + self.p.x10 - - def V2Close(self, t: float): - if t < self.T2["t1"]: - return self.p.a2 * t - t -= self.T2["t1"] - if t < self.T2["t2"]: - return self.p.a2 * self.T2["t1"] - t -= self.T2["t2"] - return self.p.a2 * self.T2["t1"] - self.p.a2 * t - - def X2Close(self, t: float): - t1 = min(t, self.T2["t1"]) - x0 = self.p.a2 * t1 * t1 / 2 - - t2 = max(min(t - self.T2["t1"], self.T2["t2"]), 0) - x1 = self.p.a2 * self.T2["t1"] * t2 - - t3 = max(min(t - self.T2["t2"]- self.T2["t1"], self.T2["t1"]), 0) - x2 = self.p.a2 * self.T2["t1"] * t3 - self.p.a2 * t3 * t3 / 2 - - return x0 + x1 + x2 + self.p.x20 - - def FClose(self, t: float): - return 0 - - def V1Grow(self, t: float): - F = self.FGrow(t) - dF0 = self.p.a * self.Ts["t1"] * self.p.k - if t < self.Ts["tm"]: - dF = sqrt(self.p.k / self.p.m) * self.p.umax / self.p.l * sin(sqrt(self.p.k / self.p.m) * t) + dF0 * cos(sqrt(self.p.k / self.p.m) * t) - return dF / self.p.k - if t < self.Ts["tend"]: - return sqrt(self.p.k/self.p.m)*sqrt((self.p.Fd-self.p.Fprop)**2 - F**2) / self.p.k - v0 = sqrt(self.p.k/self.p.m)*sqrt((self.p.Fd-self.p.Fprop)**2 - self.p.Fq**2) - b = (1/3 * v0 / cbrt((self.p.Fd - self.p.Fq))**2)**3 - dF = 3.0*b*cbrt((F -self.p.Fd)/b)**2 - return dF / self.p.k - - def X1Grow(self, t: float): - F = self.FGrow(t) - x = F / self.p.k - return x + self.x1Contact - - def V2Grow(self, t: float): - """Считается, что верхний электрод не влияет на набор усилия, функция не реализована!, возвращает 0. Устанавливайте kturn = 0 - """ - return 0 - - def X2Grow(self, t: float): - """Считается, что верхний электрод не влияет на набор усилия, функция не реализована!, возвращает 0. Устанавливайте kturn = 0 - """ - return self.x2Contact - - def FGrow(self, t: float): - v0 = self.p.a * self.Ts["t1"] - dF0 = self.p.a * self.Ts["t1"] * self.p.k - Fm = (self.p.Ftg**2 - self.p.m/self.p.k*dF0**2)/(2 * self.p.awork * self.p.m) - if t < self.Ts["tm"]: - return - self.p.umax / self.p.l * cos(sqrt(self.p.k / self.p.m) * t) + self.p.umax / self.p.l + sqrt(self.p.m / self.p.k) * dF0 * sin(sqrt(self.p.k / self.p.m) * t) - t -= self.Ts["tm"] - if t < self.Ts["tend"]: - tm = arcsin(Fm/(self.p.Ftg)) * sqrt(self.p.m/self.p.k) - return self.p.Ftg * sin(sqrt(self.p.k / self.p.m)*(t + tm)) - t -= self.Ts["tend"] - - - a = self.p.Fd - v0 = sqrt(self.p.k/self.p.m)*sqrt((self.p.Fd-self.p.Fprop)**2 - self.p.Fq**2) - b = (1/3 * v0 / cbrt((self.p.Fd - self.p.Fq))**2)**3 - q = self.p.Fq - - return 3 * t**2 * cbrt(b*b*(q-a)) + 3 * t * cbrt(q-a)**2 * cbrt(b) + b * t**3 + q - - def V1Open(self, t: float): - if t < self.Ts["to1"]: - return -self.p.a * t - t -= self.Ts["to1"] - if t < self.Ts["to2"]: - return -self.p.a * self.Ts["to1"] - t -= self.Ts["to2"] - if t < self.Ts["to1"]: - return -self.p.a * self.Ts["to1"] + self.p.a * t - return 0 - - def X1Open(self, t: float): - xm = self.p.Fd / self.p.k - t1 = min(t, self.Ts["to1"]) - x0 = -self.p.a * t1 * t1 / 2 - - t2 = max(min(t - self.Ts["to1"], self.Ts["to2"]), 0) - x1 = -self.p.a * self.Ts["to1"] * t2 - - t3 = max(min(t - self.Ts["to2"]- self.Ts["to1"], self.Ts["to1"]), 0) - x2 = -self.p.a * self.Ts["to1"] * t3 + self.p.a * t3 * t3 / 2 - - return xm + x0 + x1 + x2 + self.x1Contact - - def V2Open(self, t: float): - - t = max(t-self.TStartOpen , 0) - if t < self.T2["to1"]: - return -self.p.a2 * t - t -= self.T2["to1"] - if t < self.T2["to2"]: - return -self.p.a2 * self.T2["to1"] - t -= self.T2["to2"] - if t < self.T2["to1"]: - return -self.p.a2 * self.T2["to1"] + self.p.a2 * t - return 0 - - def X2Open(self, t: float): - t = max(t-self.TStartOpen , 0) - t1 = min(t, self.T2["to1"]) - x0 = -self.p.a2 * t1 * t1 / 2 - - t2 = max(min(t - self.T2["to1"], self.T2["to2"]), 0) - x1 = -self.p.a2 * self.T2["to1"] * t2 - - t3 = max(min(t - self.T2["to2"]- self.T2["to1"], self.T2["to1"]), 0) - x2 = -self.p.a2 * self.T2["to1"] * t3 + self.p.a2 * t3 * t3 / 2 - - return x0 + x1 + x2 + self.x2Contact - - def FOpen(self, t: float): - x1 = self.X1Open(t) - x2 = self.X2Open(t) - F = self.p.k * max(0, (x1 + x2 - self.x1Contact - self.x2Contact)) - return F - - def calcPhaseClose(self, t: float): - return self.X1Close(t), self.X2Close(t), self.V1Close(t), self.V2Close(t), self.FClose(t) - - def calcPhaseGrow(self, t: float): - return self.X1Grow(t), self.X2Grow(t), self.V1Grow(t), self.V2Grow(t), self.FGrow(t) - - def calcPhaseOpen(self, t: float): - return self.X1Open(t), self.X2Open(t), self.V1Open(t), self.V2Open(t), self.FOpen(t) - - def getSpecific(self, param : str, phase : str, t : float): - """Получить значение величины в определенную фазу в момент времени t (с начала фазы) - - Args: - param (str): Значение из списка X1 | X2 | V1 | V2 | F - phase (str): Значение из списка: Close | Grow | Open - t (float): Время - - Returns: - Значение величины - """ - funcName = param + phase - try: - func = getattr(self, funcName) - except: - print("Wrong param or phase name") - return 0 - return func(t) - - def getVar(self, param : str, t : float): - if t < self.Ts["tclose"]: - return self.getSpecific(param, "Close", t) - t -= self.Ts["tclose"] - if t < self.Ts["tgrow"] : - return self.getSpecific(param, "Grow", t) - t -= self.Ts["tgrow"] - return self.getSpecific(param, "Open", t) - -if __name__ == "__main__": - opt = OptAlgorithm() - import matplotlib.pyplot as plt - from matplotlib import use - - print(opt.Ts) - print(opt.calcPhaseClose(opt.Ts["tclose"])) - print(opt.calcPhaseGrow(opt.Ts["tgrow"])) - print(opt.calcPhaseOpen(opt.Ts["topen"])) - print(opt.getSpecific("X1", "Close", 0)) - - - use("GTK4Agg", force = True) - t = linspace(0, 0.5, 50000) - V1 = [opt.getVar("V1", tt) for tt in t] - V2 = [opt.getVar("V2", tt) for tt in t] - plt.plot(t, V2) - plt.plot(t, V1) - #plt.legend() - plt.show() - \ No newline at end of file diff --git a/OptTimeCalculator.py b/OptTimeCalculator.py deleted file mode 100644 index f659eb7..0000000 --- a/OptTimeCalculator.py +++ /dev/null @@ -1,148 +0,0 @@ -from numpy import sqrt, arcsin, arccos, cos, sin - -from scipy.optimize import minimize -import numpy - -from Params import Params - - - -class OptTimeCalculator(): - - def __init__(self, params : Params): - self.Ts = {} - self.params = params - self.Tmax = 1 - - def tGrow(self, F): - return arcsin(F/(self.params.Ftg)) * sqrt(self.params.m/self.params.k) - - def T(self, s, s2 = 0, debug = False): - if hasattr(s, "__len__"): - s = s[0] - v0q = min(sqrt(2 * self.params.a * s), self.params.v1limit) - v0 = min(v0q, sqrt(1/(self.params.k*self.params.m))* self.params.Ftg) - t1 = v0 / self.params.a - - #test second - t21 = sqrt(s2/self.params.a2) - t21 = min(self.params.v2limit/self.params.a2, t21) - t22 = max(0, (s2 - (self.params.a2 * t21 * t21)) / self.params.v2limit) - T2 = t22 + 2 * t21 - - t2t = max(0, (s - (self.params.a * t1 * t1 /2)) / v0q) - #if debug: - #print("!", t1, t2t, "|", t21, t22, "|", t1+t2t, 2*t21+t22, t2t + t1 < T2) - if t2t + t1 < T2: - if debug: - print("bad time") - return 2 * self.Tmax - #print("t2", t2t) - s3 = s+((self.params.Fd - self.params.fl)/2 + self.params.fl)/self.params.k - t3 = sqrt(s3 / self.params.a) - v3max = min(t3 * self.params.a, self.params.v1limit) - t3 = v3max / self.params.a - t3q = max(0, (s3 - t3*t3*self.params.a)/v3max) - v0 = v0 * self.params.k - l = sqrt(self.params.awork**2 * self.params.m**2 + self.params.m/self.params.k * v0**2) - #print("v0", v0, v0/k) - Fmeet = (self.params.Ftg**2 - self.params.m/self.params.k*v0**2)/(2 * self.params.awork * self.params.m) - print(Fmeet) - #if debug: - #print(Fmeet) - Fq = self.params.Fq - if Fmeet > Fq: - if debug: - print("cant reach", Fmeet) - return self.Tmax - #print(Ftg - Fmeet) - if Fmeet - self.params.awork*self.params.m > l: - if debug: - print("wut") - return 3*self.Tmax - beta = self.params.awork * self.params.m - t2 = sqrt(self.params.m/self.params.k) * (arcsin((Fmeet - beta)/(l)) + arccos(sqrt(self.params.m/self.params.k) * v0/l)) - if debug: - qtq = sqrt(self.params.k/self.params.m) - Fqq = -self.params.awork*self.params.m*cos(qtq*t2) + self.params.awork*self.params.m + v0 / qtq * sin(qtq*t2) - print("angles", (Fmeet / (2*beta) -beta)/(l), (sqrt(self.params.m/self.params.k) * v0/l), Fqq, Fmeet) - tend = self.tGrow(Fq) - self.tGrow(Fmeet) - vp = 1/sqrt(self.params.k * self.params.m) * sqrt(self.params.Ftg**2 - self.params.Fq**2) - ap = Fq / self.params.m - tprop = 2*vp / ap - #print(s, t1, t2, Fmeet, tend) - T = t1 + t2t + t2 + 2*t3 + t3q + tprop + tend - - self.Ts = {"t1":t1, "t2":t2t, "tm":t2, "tend":tend, "t4":tprop, "to1":t3, "to2": t3q, "T":T, - "tclose":t1+t2t, "tgrow":t2+tend+tprop, "topen": 2*t3+t3q} - if debug: - print("phases", t1, t2t, "|", t2, tend, tprop, "|", 2*t3+t3q, "|", T) - print("tclose: ",t1+t2t, "tgrow:", t2+tend+tprop, "topen:", 2*t3+t3q, "all:", T) - return T - - def calcSecond(self, Tstart, s2): - T1 = self.Ts["tclose"] - t1 = T1 / 2 - sqrt(T1**2 - 4 * s2 / self.params.a2) / 2 - t2 = sqrt(T1 * T1 - 4 * s2 / self.params.a2) - - T2 = self.Ts["topen"] - Tstart - to1 = T2 / 2 - sqrt(T2**2 - 4 * s2 / self.params.a2) / 2 - to2 = sqrt(T2 * T2 - 4 * s2 / self.params.a2) - - Ts = {"t1":t1, "t2":t2, "to1":to1, "to2": to2} - self.T2 = Ts - return self.T2 - - def calcOpt(self): - s0 = [0.04] - bnds = [(0.00001, None)] - res = minimize(self.T, s0, method='Nelder-Mead', tol=1e-7, bounds=bnds) - nonbound = res.x - bound = res.x - if nonbound < self.params.smin1: - #print("IS SMIN") - bound = max(nonbound, self.params.smin1) - #T(q, debug = True) - return nonbound, bound - - def showPlot(self): - - N = 50000 - ss = numpy.linspace(0.0001, 0.030, N) - Ts = numpy.array([self.T(si) for si in ss]) - - import matplotlib.pyplot as plt - from matplotlib import use - - q, qq = self.calcOpt() - q = 1000*q - qq = 1000 * qq - use("GTK4Agg", force = True) - plt.plot(ss*1000, Ts*1000, "red", label = "T(S)") - plt.plot(numpy.ones(N) * qq, Ts*1000, label = "factOpt") - plt.plot(numpy.ones(N) * q, Ts*1000, "black", label = "trueOpt") - plt.title("T(s)") - plt.xlabel("s, мм") - plt.ylabel("T, мс") - plt.legend() - plt.savefig("model.png") - plt.show() - - def getTimes(self, s): - self.T(s, debug=False) - return self.Ts - - -if __name__ == "__main__": - opt = OptTimeCalculator() - nonbound, bound = opt.calcOpt() - - print("nonbound", nonbound*1000, "мм") - print(opt.getTimes(nonbound)) - - print("bound", bound*1000, "мм") - print(opt.getTimes(bound)) - - - - diff --git a/params.json b/params.json deleted file mode 100644 index 3f4d809..0000000 --- a/params.json +++ /dev/null @@ -1,19 +0,0 @@ -{ - "a" : 25.41, - "dblock" : 4.5e-3, - "v1limit" : 0.108, - "a2" : 35.81, - "v2limit" : 0.678, - "m" : 257, - "k" : 1759291, - "kprop" : 0.05, - "kturn" : 0.0, - "Fd" : 5000, - "umax" : 20, - "l" : 0.00125, - "smin1" : 0.004, - "smin2" : 0.004, - "tc" : 2, - "x10" : 0.080, - "x20" : 0.080 -} \ No newline at end of file