Мы измерили частоту, двойную амплитуду входного и выходного сигнала и разницу во времени между входным и выходным сигналом для фильтра нижних частот с резистором 10 кОм и конденсатором 10 нФ в лаборатории.Оттуда мы вычислили разность фаз.
Теперь я рассчитал экспериментальное значение для функции передачи напряжения (G.exp) и хочу подогнать нелинейную модель через мою точку данных, чтобы оптимизировать мои параметры.
Все работаетхорошо, пока я не вызову функцию:
fit <- nls(G.exp ~ a*Vierpol(w.exp, C),
trace=TRUE, start=list(a=1, C=100e-9))
Сначала я попытался увеличить minFactor для решения step factor below minFactor
, установив control=nls.control(minFactor=1/8192)
, но это привело к еще меньшему шагу и minFactor.
Затем я попытался изменить начальные значения для a и C, что привело к сообщению об ошибке singular gradient
#ELK - Lowpass Filter
rm(list=ls())
setwd("C:/working/dir/ELK")
######################### Values
#Read frequency, Double Amplitude from incoming signal and outcoming signal, measured time difference and calculated phase
#from a constructed lowpass filter with 10k Ohm resistor and 10 nF capacitor
#from a csv file
freq <- read.csv("Filters.csv", sep= ";", skip = 0)[,c(1)]#frequency in kHz
AmpUa <- read.csv("Filters.csv", sep= ";", skip = 0)[,c(3)] #2*Amplitude in Volt
AmpUe <- read.csv("Filters.csv", sep= ";", skip = 0)[,c(2)] #2*Amplitude in Volt
phase <- read.csv("Filters.csv", sep= ";", skip = 0)[,c(5)] #Phase (without unit)
time <- read.csv("Filters.csv", sep= ";", skip = 0)[,c(4)] #Time difference of signals in ms
Log <- function(begin=1e-10, end=1e10) {
d <- 10^c(-99:99)
d <- d[d>=begin & d<=end]
dd <- outer(c(1:9), 10^c(-99:99))
dd <- dd[dd>=begin & dd<=end]
dlab <- do.call("expression",
lapply(seq(along=log10(d)),function(i) substitute(10^E,list(E=log10(d)[i]))))
list("big"=d, "small"=dd, "big.lab"=dlab)
}
lg <- Log()
######################### Amplitude
#function Vierpol gives back the theoretical value of the Voltage transfer function
Vierpol <- function(w, C) { # Lowpass
ZC <- (0+1i)/(-w*C)
ZR <- 10000
Ztot <- ZR+ZC
Gk <- ZR/Ztot
abs(Gk)
}
f <- freq * 1000 #transfer frequency from KHz to Hz
C <- 10e-9 #capacitor in Faraday
fg <- 1591 #Border frequence of the filter (calculated value)
x <- f/fg #ratio btw fg and data (wwg)
ch1 <- AmpUe/2 #measured Amplitude
ch2 <- AmpUa/2 #measured
wexp <- 2*pi*f #experimental angular frequency
Gexp <- ch2/ch1 #experimental value of the voltage transfer function
plot(f, Gexp, las=1, log = "x", xlim=c(10, 1e6), ylim=c(0, 1.1), xlab=expression(italic(f) ~ " [Hz]"), ylab=expression("|G("~italic(f)~")|"), axes=FALSE)
# fit to Gexp = a * Vierpol(wexp, R ,C)
#try to fit the experimental point through a non linear model and optimize the parameters a and C
fit<- nls(Gexp ~ a * Vierpol(wexp, C),
trace=TRUE, start=list(a=1, C=10e-9))
axis(1, at = lg$big, labels = lg$big.lab)
axis(1, at = lg$small, labels = FALSE, tcl = -0.25)
axis(2)
box()
#print(summary(fit))
fc <- 10^seq(1, 6, 0.01) # get the range 10Hz-> 1MHz
Gc <- predict(fit, list(wexp = 2*pi*fc)) # fit function for x
lines(fc, Gc) # draw the line
points(f, Gexp, pch=21, bg="white")
Я уже мог построить точки экспериментальных данных, но не смог уместить ни одну модельчерез точки данных.
Как мне установить модель nls в моих экспериментальных точках?
Сообщения об ошибках для справки:
fit<- nls(Gexp ~ a * Vierpol(wexp, 500, C),
+ trace=TRUE, start=list(a=1, C=10e-9), control=nls.control(minFactor=1/1024))
16.19366 : 1e+00 1e-08
7.865624 : -1.105361e-01 2.118218e-08
7.694877 : -1.051039e-01 -1.234647e-08
7.564449 : -1.046308e-01 5.939512e-09
7.511479 : -1.034139e-01 -4.054490e-09
7.500272 : -8.842691e-02 5.026213e-09
7.459853 : -8.841959e-02 -3.283024e-09
7.447777 : -7.526479e-02 3.808724e-09
7.399803 : -7.384654e-02 -1.698359e-09
7.351996 : -7.276184e-02 1.177592e-10
7.350372 : -1.259269e-01 2.873937e-11
Error in nls(Gexp ~ a * Vierpol(wexp, 500, C), trace = TRUE, start = list(a = 1, : step factor reduced 0.000488281 below 'minFactor' 0.000976562
fit<- nls(Gexp ~ a * Vierpol(wexp, C),
+ trace=TRUE, start=list(a=9.570e-01, C=1.948e-07))
15.52989 : 9.570e-01 1.948e-07
4.054572 : 2.187341e-01 8.618412e-06
Error in nls(Gexp ~ a * Vierpol(wexp, C), trace = TRUE, start = list(a = 0.957, : singulärer Gradient
Редактировать:
Я добавил изображение моей модели.Я не понимаю, как поможет добавление runif
для расширения диапазона ошибок.
fit<- nls(Gexp ~ a * Vierpol(wexp, C) + runif(Some_val),
trace=TRUE, start=list(a=1, C=10e-9))
Я пробовал разные значения для Some_val
, как я могу определить диапазон ошибок?
В любом случае, я 'm снова:
Ошибка в nls (Gexp ~ a * Vierpol (wexp, C) + runif (7, 8, 9), trace = TRUE,: Schrittweitenfaktor 0.000488281 unter 'minFactor' 0.000976562 reduziertКроме того: было 50 или более предупреждений (используйте предупреждения (), чтобы увидеть первые 50)
![Image of model](https://i.stack.imgur.com/1yufm.png)