# Import minpac.lm for Levenberg-Marquardt algorithm library(minpack.lm) # Open dialog to select text data file data <- read.table(file.choose()) # Separate the data into f, zr, and zi f <- data[,1,1] zr <- data[,2,1] zi <- data[,3,1] zz <- c(zr, zi) # Complex impedance data list zc <- zr + 1i*zi # Declare impedance model function imp <- function(p,x){ z <- p[1] z <- z + p[2]/(1+p[2]*p[3]*(1i*2*pi*x)^p[4]) z <- z + p[5]/(1+p[5]*p[6]*(1i*2*pi*x)^p[7]) z <- z + p[8]/(1+p[8]*p[9]*(1i*2*pi*x)^p[10]) return(z) } # Declare the residual function rsd <- function(p,z,x) { errz = imp(p,x)-z err = c(Re(errz), Im(errz)) return (err) } # Input an initial guess of the fitting parameters p0 <- c(11, 5, 5.0e-5, 0.6, 3, 1.0e-4, 0.7, 4, 1.0e-3, 0.85) # Lower limit of parameters pl <- c(0.1, 0.1, 1e-10, 0.4, 0.1, 1e-10, 0.4, 0.1, 1e-10, 0.4) # Upper limit of parameters pu <- c(50, 50, 1e-2, 1, 50, 1e-2, 1, 50, 1e-1,1) # start fitting nls.out <- nls.lm(p = p0, lower = pl, upper = pu, fn = rsd, z = zz, x = f, control = nls.lm.control(nprint = 1, maxfev = 3000, maxiter = 500, ftol = 1.0e-30)) summary(nls.out) aa <- summary(nls.out) pfit <- coef(nls.out) perr <- aa[[8]][11:20] fcov <- vcov(nls.out) RSS <- sum(abs(imp(pfit,f)-zc)*abs(imp(pfit,f)-zc)) while (aa[[5]] != 1){ p0 <- pfit nls.out <- nls.lm(p = p0, lower = pl, upper = pu, fn = rsd, z = zc, x = f, control = nls.lm.control(nprint = 1, maxfev = 3000, maxiter = 500, ftol = 0.00001)) summary(nls.out) aa <- summary(nls.out) } summary(nls.out) aa <- summary(nls.out) pfit <- coef(nls.out) perr <- aa[[8]][11:20] RSS <- sum(abs(imp(pfit,f)-zc)*abs(imp(pfit,f)-zc)) zc_cal <- imp(pfit,f) zr_cal <- Re(zc_cal) zi_cal <- Im(zc_cal) plot(f,zr,log="x", xlim=c(10^-2, 10^6),ylim=c(10, 25),ann=F) par(new=T) plot(f,zr_cal,log="x", xlim=c(10^-2, 10^6),ylim=c(10, 25), type="l") dev.new() plot(f,zi,log="x", xlim=c(10^-2, 10^6),ylim=c(-2.5, 0.5),ann=F) par(new=T) plot(f,zi_cal,log="x", xlim=c(10^-2, 10^6),ylim=c(-2.5, 0.5),type="l") dev.new() plot(zr,-zi,xlim=c(10,25),ylim=c(-2, 5),ann=F, asp = 1) par(new=T) plot(zr_cal,-zi_cal, xlim=c(10,25),ylim=c(-2, 5), type="l", asp = 1) pfit perr RSS